aboutsummaryrefslogtreecommitdiffstats
path: root/sdk_common/src/com/android/ide/common/rendering/LayoutLibrary.java
diff options
context:
space:
mode:
Diffstat (limited to 'sdk_common/src/com/android/ide/common/rendering/LayoutLibrary.java')
-rw-r--r--sdk_common/src/com/android/ide/common/rendering/LayoutLibrary.java755
1 files changed, 0 insertions, 755 deletions
diff --git a/sdk_common/src/com/android/ide/common/rendering/LayoutLibrary.java b/sdk_common/src/com/android/ide/common/rendering/LayoutLibrary.java
deleted file mode 100644
index 0a353f9..0000000
--- a/sdk_common/src/com/android/ide/common/rendering/LayoutLibrary.java
+++ /dev/null
@@ -1,755 +0,0 @@
-/*
- * Copyright (C) 2010 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.ide.common.rendering;
-
-import static com.android.ide.common.rendering.api.Result.Status.ERROR_REFLECTION;
-
-import com.android.ide.common.rendering.api.Bridge;
-import com.android.ide.common.rendering.api.Capability;
-import com.android.ide.common.rendering.api.DrawableParams;
-import com.android.ide.common.rendering.api.ILayoutPullParser;
-import com.android.ide.common.rendering.api.LayoutLog;
-import com.android.ide.common.rendering.api.RenderSession;
-import com.android.ide.common.rendering.api.ResourceValue;
-import com.android.ide.common.rendering.api.Result;
-import com.android.ide.common.rendering.api.Result.Status;
-import com.android.ide.common.rendering.api.SessionParams;
-import com.android.ide.common.rendering.api.SessionParams.RenderingMode;
-import com.android.ide.common.rendering.api.ViewInfo;
-import com.android.ide.common.rendering.legacy.ILegacyPullParser;
-import com.android.ide.common.rendering.legacy.LegacyCallback;
-import com.android.ide.common.resources.ResourceResolver;
-import com.android.ide.common.sdk.LoadStatus;
-import com.android.layoutlib.api.ILayoutBridge;
-import com.android.layoutlib.api.ILayoutLog;
-import com.android.layoutlib.api.ILayoutResult;
-import com.android.layoutlib.api.ILayoutResult.ILayoutViewInfo;
-import com.android.layoutlib.api.IProjectCallback;
-import com.android.layoutlib.api.IResourceValue;
-import com.android.layoutlib.api.IXmlPullParser;
-import com.android.resources.ResourceType;
-import com.android.utils.ILogger;
-
-import java.awt.image.BufferedImage;
-import java.io.File;
-import java.lang.reflect.Constructor;
-import java.lang.reflect.Field;
-import java.lang.reflect.Method;
-import java.net.URI;
-import java.net.URL;
-import java.net.URLClassLoader;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.Map.Entry;
-
-/**
- * Class to use the Layout library.
- * <p/>
- * Use {@link #load(String, ILogger)} to load the jar file.
- * <p/>
- * Use the layout library with:
- * {@link #init(String, Map)}, {@link #supports(Capability)}, {@link #createSession(SessionParams)},
- * {@link #dispose()}, {@link #clearCaches(Object)}.
- *
- * <p/>
- * For client wanting to access both new and old (pre API level 5) layout libraries, it is
- * important that the following interfaces be used:<br>
- * {@link ILegacyPullParser} instead of {@link ILayoutPullParser}<br>
- * {@link LegacyCallback} instead of {@link com.android.ide.common.rendering.api.IProjectCallback}.
- * <p/>
- * These interfaces will ensure that both new and older Layout libraries can be accessed.
- */
-@SuppressWarnings("deprecation")
-public class LayoutLibrary {
-
- public final static String CLASS_BRIDGE = "com.android.layoutlib.bridge.Bridge"; //$NON-NLS-1$
-
- /** Link to the layout bridge */
- private final Bridge mBridge;
- /** Link to a ILayoutBridge in case loaded an older library */
- private final ILayoutBridge mLegacyBridge;
- /** Status of the layoutlib.jar loading */
- private final LoadStatus mStatus;
- /** Message associated with the {@link LoadStatus}. This is mostly used when
- * {@link #getStatus()} returns {@link LoadStatus#FAILED}.
- */
- private final String mLoadMessage;
- /** classloader used to load the jar file */
- private final ClassLoader mClassLoader;
-
- // Reflection data for older Layout Libraries.
- private Method mViewGetParentMethod;
- private Method mViewGetBaselineMethod;
- private Method mViewParentIndexOfChildMethod;
- private Class<?> mMarginLayoutParamClass;
- private Field mLeftMarginField;
- private Field mTopMarginField;
- private Field mRightMarginField;
- private Field mBottomMarginField;
-
- /**
- * Returns the {@link LoadStatus} of the loading of the layoutlib jar file.
- */
- public LoadStatus getStatus() {
- return mStatus;
- }
-
- /** Returns the message associated with the {@link LoadStatus}. This is mostly used when
- * {@link #getStatus()} returns {@link LoadStatus#FAILED}.
- */
- public String getLoadMessage() {
- return mLoadMessage;
- }
-
- /**
- * Returns the classloader used to load the classes in the layoutlib jar file.
- */
- public ClassLoader getClassLoader() {
- return mClassLoader;
- }
-
- /**
- * Loads the layoutlib.jar file located at the given path and returns a {@link LayoutLibrary}
- * object representing the result.
- * <p/>
- * If loading failed {@link #getStatus()} will reflect this, and {@link #getBridge()} will
- * return null.
- *
- * @param layoutLibJarOsPath the path of the jar file
- * @param log an optional log file.
- * @return a {@link LayoutLibrary} object always.
- */
- public static LayoutLibrary load(String layoutLibJarOsPath, ILogger log, String toolName) {
-
- LoadStatus status = LoadStatus.LOADING;
- String message = null;
- Bridge bridge = null;
- ILayoutBridge legacyBridge = null;
- ClassLoader classLoader = null;
-
- try {
- // get the URL for the file.
- File f = new File(layoutLibJarOsPath);
- if (f.isFile() == false) {
- if (log != null) {
- log.error(null, "layoutlib.jar is missing!"); //$NON-NLS-1$
- }
- } else {
- URI uri = f.toURI();
- URL url = uri.toURL();
-
- // create a class loader. Because this jar reference interfaces
- // that are in the editors plugin, it's important to provide
- // a parent class loader.
- classLoader = new URLClassLoader(
- new URL[] { url },
- LayoutLibrary.class.getClassLoader());
-
- // load the class
- Class<?> clazz = classLoader.loadClass(CLASS_BRIDGE);
- if (clazz != null) {
- // instantiate an object of the class.
- Constructor<?> constructor = clazz.getConstructor();
- if (constructor != null) {
- Object bridgeObject = constructor.newInstance();
- if (bridgeObject instanceof Bridge) {
- bridge = (Bridge)bridgeObject;
- } else if (bridgeObject instanceof ILayoutBridge) {
- legacyBridge = (ILayoutBridge) bridgeObject;
- }
- }
- }
-
- if (bridge == null && legacyBridge == null) {
- status = LoadStatus.FAILED;
- message = "Failed to load " + CLASS_BRIDGE; //$NON-NLS-1$
- if (log != null) {
- log.error(null,
- "Failed to load " + //$NON-NLS-1$
- CLASS_BRIDGE +
- " from " + //$NON-NLS-1$
- layoutLibJarOsPath);
- }
- } else {
- // mark the lib as loaded, unless it's overridden below.
- status = LoadStatus.LOADED;
-
- // check the API, only if it's not a legacy bridge
- if (bridge != null) {
- int api = bridge.getApiLevel();
- if (api > Bridge.API_CURRENT) {
- status = LoadStatus.FAILED;
- message = String.format(
- "This version of the rendering library is more recent than your version of %1$s. Please update %1$s", toolName);
- }
- }
- }
- }
- } catch (Throwable t) {
- status = LoadStatus.FAILED;
- Throwable cause = t;
- while (cause.getCause() != null) {
- cause = cause.getCause();
- }
- message = "Failed to load the LayoutLib: " + cause.getMessage();
- // log the error.
- if (log != null) {
- log.error(t, message);
- }
- }
-
- return new LayoutLibrary(bridge, legacyBridge, classLoader, status, message);
- }
-
- // ------ Layout Lib API proxy
-
- /**
- * Returns the API level of the layout library.
- */
- public int getApiLevel() {
- if (mBridge != null) {
- return mBridge.getApiLevel();
- }
-
- if (mLegacyBridge != null) {
- return getLegacyApiLevel();
- }
-
- return 0;
- }
-
- /**
- * Returns the revision of the library inside a given (layoutlib) API level.
- * The true version number of the library is {@link #getApiLevel()}.{@link #getRevision()}
- */
- public int getRevision() {
- if (mBridge != null) {
- return mBridge.getRevision();
- }
-
- return 0;
- }
-
- /**
- * Returns whether the LayoutLibrary supports a given {@link Capability}.
- * @return true if it supports it.
- *
- * @see Bridge#getCapabilities()
- *
- */
- public boolean supports(Capability capability) {
- if (mBridge != null) {
- return mBridge.getCapabilities().contains(capability);
- }
-
- if (mLegacyBridge != null) {
- switch (capability) {
- case UNBOUND_RENDERING:
- // legacy stops at 4. 5 is new API.
- return getLegacyApiLevel() == 4;
- }
- }
-
- return false;
- }
-
- /**
- * Initializes the Layout Library object. This must be called before any other action is taken
- * on the instance.
- *
- * @param platformProperties The build properties for the platform.
- * @param fontLocation the location of the fonts in the SDK target.
- * @param enumValueMap map attrName => { map enumFlagName => Integer value }. This is typically
- * read from attrs.xml in the SDK target.
- * @param log a {@link LayoutLog} object. Can be null.
- * @return true if success.
- *
- * @see Bridge#init(String, Map)
- */
- public boolean init(Map<String, String> platformProperties,
- File fontLocation,
- Map<String, Map<String, Integer>> enumValueMap,
- LayoutLog log) {
- if (mBridge != null) {
- return mBridge.init(platformProperties, fontLocation, enumValueMap, log);
- } else if (mLegacyBridge != null) {
- return mLegacyBridge.init(fontLocation.getAbsolutePath(), enumValueMap);
- }
-
- return false;
- }
-
- /**
- * Prepares the layoutlib to unloaded.
- *
- * @see Bridge#dispose()
- */
- public boolean dispose() {
- if (mBridge != null) {
- return mBridge.dispose();
- }
-
- return true;
- }
-
- /**
- * Starts a layout session by inflating and rendering it. The method returns a
- * {@link RenderSession} on which further actions can be taken.
- * <p/>
- * Before taking further actions on the scene, it is recommended to use
- * {@link #supports(Capability)} to check what the scene can do.
- *
- * @return a new {@link ILayoutScene} object that contains the result of the scene creation and
- * first rendering or null if {@link #getStatus()} doesn't return {@link LoadStatus#LOADED}.
- *
- * @see Bridge#createSession(SessionParams)
- */
- public RenderSession createSession(SessionParams params) {
- if (mBridge != null) {
- RenderSession session = mBridge.createSession(params);
- if (params.getExtendedViewInfoMode() &&
- mBridge.getCapabilities().contains(Capability.EXTENDED_VIEWINFO) == false) {
- // Extended view info was requested but the layoutlib does not support it.
- // Add it manually.
- List<ViewInfo> infoList = session.getRootViews();
- if (infoList != null) {
- for (ViewInfo info : infoList) {
- addExtendedViewInfo(info);
- }
- }
- }
-
- return session;
- } else if (mLegacyBridge != null) {
- return createLegacySession(params);
- }
-
- return null;
- }
-
- /**
- * Renders a Drawable. If the rendering is successful, the result image is accessible through
- * {@link Result#getData()}. It is of type {@link BufferedImage}
- * @param params the rendering parameters.
- * @return the result of the action.
- */
- public Result renderDrawable(DrawableParams params) {
- if (mBridge != null) {
- return mBridge.renderDrawable(params);
- }
-
- return Status.NOT_IMPLEMENTED.createResult();
- }
-
- /**
- * Clears the resource cache for a specific project.
- * <p/>This cache contains bitmaps and nine patches that are loaded from the disk and reused
- * until this method is called.
- * <p/>The cache is not configuration dependent and should only be cleared when a
- * resource changes (at this time only bitmaps and 9 patches go into the cache).
- *
- * @param projectKey the key for the project.
- *
- * @see Bridge#clearCaches(Object)
- */
- public void clearCaches(Object projectKey) {
- if (mBridge != null) {
- mBridge.clearCaches(projectKey);
- } else if (mLegacyBridge != null) {
- mLegacyBridge.clearCaches(projectKey);
- }
- }
-
- /**
- * Utility method returning the parent of a given view object.
- *
- * @param viewObject the object for which to return the parent.
- *
- * @return a {@link Result} indicating the status of the action, and if success, the parent
- * object in {@link Result#getData()}
- */
- public Result getViewParent(Object viewObject) {
- if (mBridge != null) {
- Result r = mBridge.getViewParent(viewObject);
- if (r.isSuccess()) {
- return r;
- }
- }
-
- return getViewParentWithReflection(viewObject);
- }
-
- /**
- * Utility method returning the index of a given view in its parent.
- * @param viewObject the object for which to return the index.
- *
- * @return a {@link Result} indicating the status of the action, and if success, the index in
- * the parent in {@link Result#getData()}
- */
- public Result getViewIndex(Object viewObject) {
- if (mBridge != null) {
- Result r = mBridge.getViewIndex(viewObject);
- if (r.isSuccess()) {
- return r;
- }
- }
-
- return getViewIndexReflection(viewObject);
- }
-
- // ------ Implementation
-
- private LayoutLibrary(Bridge bridge, ILayoutBridge legacyBridge, ClassLoader classLoader,
- LoadStatus status, String message) {
- mBridge = bridge;
- mLegacyBridge = legacyBridge;
- mClassLoader = classLoader;
- mStatus = status;
- mLoadMessage = message;
- }
-
- /**
- * Returns the API level of the legacy bridge.
- * <p/>
- * This handles the case where ILayoutBridge does not have a {@link ILayoutBridge#getApiLevel()}
- * (at API level 1).
- * <p/>
- * {@link ILayoutBridge#getApiLevel()} should never called directly.
- *
- * @return the api level of {@link #mLegacyBridge}.
- */
- private int getLegacyApiLevel() {
- int apiLevel = 1;
- try {
- apiLevel = mLegacyBridge.getApiLevel();
- } catch (AbstractMethodError e) {
- // the first version of the api did not have this method
- // so this is 1
- }
-
- return apiLevel;
- }
-
- private RenderSession createLegacySession(SessionParams params) {
- if (params.getLayoutDescription() instanceof IXmlPullParser == false) {
- throw new IllegalArgumentException("Parser must be of type ILegacyPullParser");
- }
- if (params.getProjectCallback() instanceof
- com.android.layoutlib.api.IProjectCallback == false) {
- throw new IllegalArgumentException("Project callback must be of type ILegacyCallback");
- }
-
- if (params.getResources() instanceof ResourceResolver == false) {
- throw new IllegalArgumentException("RenderResources object must be of type ResourceResolver");
- }
-
- ResourceResolver resources = (ResourceResolver) params.getResources();
-
- int apiLevel = getLegacyApiLevel();
-
- // create a log wrapper since the older api requires a ILayoutLog
- final LayoutLog log = params.getLog();
- ILayoutLog logWrapper = new ILayoutLog() {
-
- @Override
- public void warning(String message) {
- log.warning(null, message, null /*data*/);
- }
-
- @Override
- public void error(Throwable t) {
- log.error(null, "error!", t, null /*data*/);
- }
-
- @Override
- public void error(String message) {
- log.error(null, message, null /*data*/);
- }
- };
-
-
- // convert the map of ResourceValue into IResourceValue. Super ugly but works.
-
- Map<String, Map<String, IResourceValue>> projectMap = convertMap(
- resources.getProjectResources());
- Map<String, Map<String, IResourceValue>> frameworkMap = convertMap(
- resources.getFrameworkResources());
-
- ILayoutResult result = null;
-
- if (apiLevel == 4) {
- // Final ILayoutBridge API added support for "render full height"
- result = mLegacyBridge.computeLayout(
- (IXmlPullParser) params.getLayoutDescription(),
- params.getProjectKey(),
- params.getScreenWidth(), params.getScreenHeight(),
- params.getRenderingMode() == RenderingMode.FULL_EXPAND ? true : false,
- params.getDensity().getDpiValue(), params.getXdpi(), params.getYdpi(),
- resources.getThemeName(), resources.isProjectTheme(),
- projectMap, frameworkMap,
- (IProjectCallback) params.getProjectCallback(),
- logWrapper);
- } else if (apiLevel == 3) {
- // api 3 add density support.
- result = mLegacyBridge.computeLayout(
- (IXmlPullParser) params.getLayoutDescription(), params.getProjectKey(),
- params.getScreenWidth(), params.getScreenHeight(),
- params.getDensity().getDpiValue(), params.getXdpi(), params.getYdpi(),
- resources.getThemeName(), resources.isProjectTheme(),
- projectMap, frameworkMap,
- (IProjectCallback) params.getProjectCallback(), logWrapper);
- } else if (apiLevel == 2) {
- // api 2 added boolean for separation of project/framework theme
- result = mLegacyBridge.computeLayout(
- (IXmlPullParser) params.getLayoutDescription(), params.getProjectKey(),
- params.getScreenWidth(), params.getScreenHeight(),
- resources.getThemeName(), resources.isProjectTheme(),
- projectMap, frameworkMap,
- (IProjectCallback) params.getProjectCallback(), logWrapper);
- } else {
- // First api with no density/dpi, and project theme boolean mixed
- // into the theme name.
-
- // change the string if it's a custom theme to make sure we can
- // differentiate them
- String themeName = resources.getThemeName();
- if (resources.isProjectTheme()) {
- themeName = "*" + themeName; //$NON-NLS-1$
- }
-
- result = mLegacyBridge.computeLayout(
- (IXmlPullParser) params.getLayoutDescription(), params.getProjectKey(),
- params.getScreenWidth(), params.getScreenHeight(),
- themeName,
- projectMap, frameworkMap,
- (IProjectCallback) params.getProjectCallback(), logWrapper);
- }
-
- // clean up that is not done by the ILayoutBridge itself
- legacyCleanUp();
-
- return convertToScene(result);
- }
-
- @SuppressWarnings("unchecked")
- private Map<String, Map<String, IResourceValue>> convertMap(
- Map<ResourceType, Map<String, ResourceValue>> map) {
- Map<String, Map<String, IResourceValue>> result =
- new HashMap<String, Map<String, IResourceValue>>();
-
- for (Entry<ResourceType, Map<String, ResourceValue>> entry : map.entrySet()) {
- // ugly case but works.
- result.put(entry.getKey().getName(),
- (Map) entry.getValue());
- }
-
- return result;
- }
-
- /**
- * Converts a {@link ILayoutResult} to a {@link RenderSession}.
- */
- private RenderSession convertToScene(ILayoutResult result) {
-
- Result sceneResult;
- ViewInfo rootViewInfo = null;
-
- if (result.getSuccess() == ILayoutResult.SUCCESS) {
- sceneResult = Status.SUCCESS.createResult();
- ILayoutViewInfo oldRootView = result.getRootView();
- if (oldRootView != null) {
- rootViewInfo = convertToViewInfo(oldRootView);
- }
- } else {
- sceneResult = Status.ERROR_UNKNOWN.createResult(result.getErrorMessage());
- }
-
- // create a BasicLayoutScene. This will return the given values but return the default
- // implementation for all method.
- // ADT should gracefully handle the default implementations of LayoutScene
- return new StaticRenderSession(sceneResult, rootViewInfo, result.getImage());
- }
-
- /**
- * Converts a {@link ILayoutViewInfo} (and its children) to a {@link ViewInfo}.
- */
- private ViewInfo convertToViewInfo(ILayoutViewInfo view) {
- // create the view info.
- ViewInfo viewInfo = new ViewInfo(view.getName(), view.getViewKey(),
- view.getLeft(), view.getTop(), view.getRight(), view.getBottom());
-
- // then convert the children
- ILayoutViewInfo[] children = view.getChildren();
- if (children != null) {
- ArrayList<ViewInfo> convertedChildren = new ArrayList<ViewInfo>(children.length);
- for (ILayoutViewInfo child : children) {
- convertedChildren.add(convertToViewInfo(child));
- }
- viewInfo.setChildren(convertedChildren);
- }
-
- return viewInfo;
- }
-
- /**
- * Post rendering clean-up that must be done here because it's not done in any layoutlib using
- * {@link ILayoutBridge}.
- */
- private void legacyCleanUp() {
- try {
- Class<?> looperClass = mClassLoader.loadClass("android.os.Looper"); //$NON-NLS-1$
- Field threadLocalField = looperClass.getField("sThreadLocal"); //$NON-NLS-1$
- if (threadLocalField != null) {
- threadLocalField.setAccessible(true);
- // get object. Field is static so no need to pass an object
- ThreadLocal<?> threadLocal = (ThreadLocal<?>) threadLocalField.get(null);
- if (threadLocal != null) {
- threadLocal.remove();
- }
- }
- } catch (Exception e) {
- // do nothing.
- }
- }
-
- private Result getViewParentWithReflection(Object viewObject) {
- // default implementation using reflection.
- try {
- if (mViewGetParentMethod == null) {
- Class<?> viewClass = Class.forName("android.view.View");
- mViewGetParentMethod = viewClass.getMethod("getParent");
- }
-
- return Status.SUCCESS.createResult(mViewGetParentMethod.invoke(viewObject));
- } catch (Exception e) {
- // Catch all for the reflection calls.
- return ERROR_REFLECTION.createResult(null, e);
- }
- }
-
- /**
- * Utility method returning the index of a given view in its parent.
- * @param viewObject the object for which to return the index.
- *
- * @return a {@link Result} indicating the status of the action, and if success, the index in
- * the parent in {@link Result#getData()}
- */
- private Result getViewIndexReflection(Object viewObject) {
- // default implementation using reflection.
- try {
- Class<?> viewClass = Class.forName("android.view.View");
-
- if (mViewGetParentMethod == null) {
- mViewGetParentMethod = viewClass.getMethod("getParent");
- }
-
- Object parentObject = mViewGetParentMethod.invoke(viewObject);
-
- if (mViewParentIndexOfChildMethod == null) {
- Class<?> viewParentClass = Class.forName("android.view.ViewParent");
- mViewParentIndexOfChildMethod = viewParentClass.getMethod("indexOfChild",
- viewClass);
- }
-
- return Status.SUCCESS.createResult(
- mViewParentIndexOfChildMethod.invoke(parentObject, viewObject));
- } catch (Exception e) {
- // Catch all for the reflection calls.
- return ERROR_REFLECTION.createResult(null, e);
- }
- }
-
- private void addExtendedViewInfo(ViewInfo info) {
- computeExtendedViewInfo(info);
-
- List<ViewInfo> children = info.getChildren();
- for (ViewInfo child : children) {
- addExtendedViewInfo(child);
- }
- }
-
- private void computeExtendedViewInfo(ViewInfo info) {
- Object viewObject = info.getViewObject();
- Object params = info.getLayoutParamsObject();
-
- int baseLine = getViewBaselineReflection(viewObject);
- int leftMargin = 0;
- int topMargin = 0;
- int rightMargin = 0;
- int bottomMargin = 0;
-
- try {
- if (mMarginLayoutParamClass == null) {
- mMarginLayoutParamClass = Class.forName(
- "android.view.ViewGroup$MarginLayoutParams");
-
- mLeftMarginField = mMarginLayoutParamClass.getField("leftMargin");
- mTopMarginField = mMarginLayoutParamClass.getField("topMargin");
- mRightMarginField = mMarginLayoutParamClass.getField("rightMargin");
- mBottomMarginField = mMarginLayoutParamClass.getField("bottomMargin");
- }
-
- if (mMarginLayoutParamClass.isAssignableFrom(params.getClass())) {
-
- leftMargin = (Integer)mLeftMarginField.get(params);
- topMargin = (Integer)mTopMarginField.get(params);
- rightMargin = (Integer)mRightMarginField.get(params);
- bottomMargin = (Integer)mBottomMarginField.get(params);
- }
-
- } catch (Exception e) {
- // just use 'unknown' value.
- leftMargin = Integer.MIN_VALUE;
- topMargin = Integer.MIN_VALUE;
- rightMargin = Integer.MIN_VALUE;
- bottomMargin = Integer.MIN_VALUE;
- }
-
- info.setExtendedInfo(baseLine, leftMargin, topMargin, rightMargin, bottomMargin);
- }
-
- /**
- * Utility method returning the baseline value for a given view object. This basically returns
- * View.getBaseline().
- *
- * @param viewObject the object for which to return the index.
- *
- * @return the baseline value or -1 if not applicable to the view object or if this layout
- * library does not implement this method.
- */
- private int getViewBaselineReflection(Object viewObject) {
- // default implementation using reflection.
- try {
- if (mViewGetBaselineMethod == null) {
- Class<?> viewClass = Class.forName("android.view.View");
- mViewGetBaselineMethod = viewClass.getMethod("getBaseline");
- }
-
- Object result = mViewGetBaselineMethod.invoke(viewObject);
- if (result instanceof Integer) {
- return ((Integer)result).intValue();
- }
-
- } catch (Exception e) {
- // Catch all for the reflection calls.
- }
-
- return Integer.MIN_VALUE;
- }
-}