use of com.android.ide.common.rendering.api.StyleResourceValue in project android_frameworks_base by ResurrectionRemix.
the class BridgeContext method obtainStyledAttributes.
@Override
public BridgeTypedArray obtainStyledAttributes(AttributeSet set, int[] attrs, int defStyleAttr, int defStyleRes) {
PropertiesMap defaultPropMap = null;
boolean isPlatformFile = true;
// Hint: for XmlPullParser, attach source //DEVICE_SRC/dalvik/libcore/xml/src/java
if (set instanceof BridgeXmlBlockParser) {
BridgeXmlBlockParser parser;
parser = (BridgeXmlBlockParser) set;
isPlatformFile = parser.isPlatformFile();
Object key = parser.getViewCookie();
if (key != null) {
defaultPropMap = mDefaultPropMaps.get(key);
if (defaultPropMap == null) {
defaultPropMap = new PropertiesMap();
mDefaultPropMaps.put(key, defaultPropMap);
}
}
} else if (set instanceof BridgeLayoutParamsMapAttributes) {
// this is only for temp layout params generated dynamically, so this is never
// platform content.
isPlatformFile = false;
} else if (set != null) {
// null parser is ok
// really this should not be happening since its instantiated in Bridge
Bridge.getLog().error(LayoutLog.TAG_BROKEN, "Parser is not a BridgeXmlBlockParser!", null);
return null;
}
List<Pair<String, Boolean>> attributeList = searchAttrs(attrs);
BridgeTypedArray ta = Resources_Delegate.newTypeArray(mSystemResources, attrs.length, isPlatformFile);
// look for a custom style.
String customStyle = null;
if (set != null) {
customStyle = set.getAttributeValue(null, "style");
}
StyleResourceValue customStyleValues = null;
if (customStyle != null) {
ResourceValue item = mRenderResources.findResValue(customStyle, isPlatformFile);
// resolve it in case it links to something else
item = mRenderResources.resolveResValue(item);
if (item instanceof StyleResourceValue) {
customStyleValues = (StyleResourceValue) item;
}
}
// resolve the defStyleAttr value into a IStyleResourceValue
StyleResourceValue defStyleValues = null;
if (defStyleAttr != 0) {
// get the name from the int.
Pair<String, Boolean> defStyleAttribute = searchAttr(defStyleAttr);
if (defStyleAttribute == null) {
// This should be rare. Happens trying to map R.style.foo to @style/foo fails.
// This will happen if the user explicitly used a non existing int value for
// defStyleAttr or there's something wrong with the project structure/build.
Bridge.getLog().error(LayoutLog.TAG_RESOURCES_RESOLVE, "Failed to find the style corresponding to the id " + defStyleAttr, null);
} else {
String defStyleName = defStyleAttribute.getFirst();
// look for the style in the current theme, and its parent:
ResourceValue item = mRenderResources.findItemInTheme(defStyleName, defStyleAttribute.getSecond());
if (item != null) {
// item is a reference to a style entry. Search for it.
item = mRenderResources.findResValue(item.getValue(), item.isFramework());
item = mRenderResources.resolveResValue(item);
if (item instanceof StyleResourceValue) {
defStyleValues = (StyleResourceValue) item;
}
if (defaultPropMap != null) {
if (defStyleAttribute.getSecond()) {
defStyleName = "android:" + defStyleName;
}
defaultPropMap.put("style", new Property(defStyleName, item.getValue()));
}
} else {
Bridge.getLog().error(LayoutLog.TAG_RESOURCES_RESOLVE_THEME_ATTR, String.format("Failed to find style '%s' in current theme", defStyleAttribute.getFirst()), null);
}
}
} else if (defStyleRes != 0) {
StyleResourceValue item = getStyleByDynamicId(defStyleRes);
if (item != null) {
defStyleValues = item;
} else {
boolean isFrameworkRes = true;
Pair<ResourceType, String> value = Bridge.resolveResourceId(defStyleRes);
if (value == null) {
value = mLayoutlibCallback.resolveResourceId(defStyleRes);
isFrameworkRes = false;
}
if (value != null) {
if ((value.getFirst() == ResourceType.STYLE)) {
// look for the style in all resources:
item = mRenderResources.getStyle(value.getSecond(), isFrameworkRes);
if (item != null) {
if (defaultPropMap != null) {
String name = item.getName();
defaultPropMap.put("style", new Property(name, name));
}
defStyleValues = item;
} else {
Bridge.getLog().error(null, String.format("Style with id 0x%x (resolved to '%s') does not exist.", defStyleRes, value.getSecond()), null);
}
} else {
Bridge.getLog().error(null, String.format("Resource id 0x%x is not of type STYLE (instead %s)", defStyleRes, value.getFirst().toString()), null);
}
} else {
Bridge.getLog().error(null, String.format("Failed to find style with id 0x%x in current theme", defStyleRes), null);
}
}
}
String appNamespace = mLayoutlibCallback.getNamespace();
if (attributeList != null) {
for (int index = 0; index < attributeList.size(); index++) {
Pair<String, Boolean> attribute = attributeList.get(index);
if (attribute == null) {
continue;
}
String attrName = attribute.getFirst();
boolean frameworkAttr = attribute.getSecond();
String value = null;
if (set != null) {
value = set.getAttributeValue(frameworkAttr ? BridgeConstants.NS_RESOURCES : appNamespace, attrName);
// new res-auto namespace as well
if (!frameworkAttr && value == null) {
value = set.getAttributeValue(BridgeConstants.NS_APP_RES_AUTO, attrName);
}
}
// values in the widget defStyle, and then in the theme.
if (value == null) {
ResourceValue resValue = null;
// look for the value in the custom style first (and its parent if needed)
if (customStyleValues != null) {
resValue = mRenderResources.findItemInStyle(customStyleValues, attrName, frameworkAttr);
}
// then look for the value in the default Style (and its parent if needed)
if (resValue == null && defStyleValues != null) {
resValue = mRenderResources.findItemInStyle(defStyleValues, attrName, frameworkAttr);
}
// its parent themes)
if (resValue == null) {
resValue = mRenderResources.findItemInTheme(attrName, frameworkAttr);
}
// So we resolve it.
if (resValue != null) {
String preResolve = resValue.getValue();
resValue = mRenderResources.resolveResValue(resValue);
if (defaultPropMap != null) {
defaultPropMap.put(frameworkAttr ? SdkConstants.PREFIX_ANDROID + attrName : attrName, new Property(preResolve, resValue.getValue()));
}
// If the value is a reference to another theme attribute that doesn't
// exist, we should log a warning and omit it.
String val = resValue.getValue();
if (val != null && val.startsWith(SdkConstants.PREFIX_THEME_REF)) {
if (!attrName.equals(RTL_ATTRS.get(val)) || getApplicationInfo().targetSdkVersion < VERSION_CODES.JELLY_BEAN_MR1) {
// Only log a warning if the referenced value isn't one of the RTL
// attributes, or the app targets old API.
Bridge.getLog().warning(LayoutLog.TAG_RESOURCES_RESOLVE_THEME_ATTR, String.format("Failed to find '%s' in current theme.", val), val);
}
resValue = null;
}
}
ta.bridgeSetValue(index, attrName, frameworkAttr, resValue);
} else {
// there is a value in the XML, but we need to resolve it in case it's
// referencing another resource or a theme value.
ta.bridgeSetValue(index, attrName, frameworkAttr, mRenderResources.resolveValue(null, attrName, value, isPlatformFile));
}
}
}
ta.sealArray();
return ta;
}
use of com.android.ide.common.rendering.api.StyleResourceValue in project android_frameworks_base by ResurrectionRemix.
the class CustomBar method setStyle.
protected void setStyle(String themeEntryName) {
BridgeContext bridgeContext = getContext();
RenderResources res = bridgeContext.getRenderResources();
ResourceValue value = res.findItemInTheme(themeEntryName, true);
value = res.resolveResValue(value);
if (!(value instanceof StyleResourceValue)) {
return;
}
StyleResourceValue style = (StyleResourceValue) value;
// get the background
ResourceValue backgroundValue = res.findItemInStyle(style, "background", true);
backgroundValue = res.resolveResValue(backgroundValue);
if (backgroundValue != null) {
Drawable d = ResourceHelper.getDrawable(backgroundValue, bridgeContext);
if (d != null) {
setBackground(d);
}
}
TextView textView = getStyleableTextView();
if (textView != null) {
// get the text style
ResourceValue textStyleValue = res.findItemInStyle(style, "titleTextStyle", true);
textStyleValue = res.resolveResValue(textStyleValue);
if (textStyleValue instanceof StyleResourceValue) {
StyleResourceValue textStyle = (StyleResourceValue) textStyleValue;
ResourceValue textSize = res.findItemInStyle(textStyle, "textSize", true);
textSize = res.resolveResValue(textSize);
if (textSize != null) {
TypedValue out = new TypedValue();
if (ResourceHelper.parseFloatAttribute("textSize", textSize.getValue(), out, true)) {
textView.setTextSize(TypedValue.COMPLEX_UNIT_PX, out.getDimension(bridgeContext.getResources().getDisplayMetrics()));
}
}
ResourceValue textColor = res.findItemInStyle(textStyle, "textColor", true);
textColor = res.resolveResValue(textColor);
if (textColor != null) {
ColorStateList stateList = ResourceHelper.getColorStateList(textColor, bridgeContext);
if (stateList != null) {
textView.setTextColor(stateList);
}
}
}
}
}
use of com.android.ide.common.rendering.api.StyleResourceValue in project android_frameworks_base by ResurrectionRemix.
the class BridgeTypedArray method getResourceId.
/**
* Retrieve the resource identifier for the attribute at
* <var>index</var>. Note that attribute resource as resolved when
* the overall {@link TypedArray} object is retrieved. As a
* result, this function will return the resource identifier of the
* final resource value that was found, <em>not</em> necessarily the
* original resource that was specified by the attribute.
*
* @param index Index of attribute to retrieve.
* @param defValue Value to return if the attribute is not defined or
* not a resource.
*
* @return Attribute resource identifier, or defValue if not defined.
*/
@Override
public int getResourceId(int index, int defValue) {
if (index < 0 || index >= mResourceData.length) {
return defValue;
}
// get the Resource for this index
ResourceValue resValue = mResourceData[index];
// no data, return the default value.
if (resValue == null) {
return defValue;
}
// check if this is a style resource
if (resValue instanceof StyleResourceValue) {
// get the id that will represent this style.
return mContext.getDynamicIdByStyle((StyleResourceValue) resValue);
}
// (and getValue() returning null!). We need to handle this!
if (resValue.getResourceType() != null) {
// if this is a framework id
if (mPlatformFile || resValue.isFramework()) {
// look for idName in the android R classes
return mContext.getFrameworkResourceValue(resValue.getResourceType(), resValue.getName(), defValue);
}
// look for idName in the project R class.
return mContext.getProjectResourceValue(resValue.getResourceType(), resValue.getName(), defValue);
}
// else, try to get the value, and resolve it somehow.
String value = resValue.getValue();
if (value == null) {
return defValue;
}
// if the value is just an integer, return it.
try {
int i = Integer.parseInt(value);
if (Integer.toString(i).equals(value)) {
return i;
}
} catch (NumberFormatException e) {
// pass
}
// if this is a reference to an id, find it.
if (value.startsWith("@id/") || value.startsWith("@+") || value.startsWith("@android:id/")) {
int pos = value.indexOf('/');
String idName = value.substring(pos + 1);
boolean create = value.startsWith("@+");
boolean isFrameworkId = mPlatformFile || value.startsWith("@android") || value.startsWith("@+android");
// Look for the idName in project or android R class depending on isPlatform.
if (create) {
Integer idValue;
if (isFrameworkId) {
idValue = Bridge.getResourceId(ResourceType.ID, idName);
} else {
idValue = mContext.getLayoutlibCallback().getResourceId(ResourceType.ID, idName);
}
return idValue == null ? defValue : idValue;
}
// one is not found.
if (isFrameworkId) {
return mContext.getFrameworkResourceValue(ResourceType.ID, idName, defValue);
} else {
return mContext.getProjectResourceValue(ResourceType.ID, idName, defValue);
}
}
// not a direct id valid reference? resolve it
Integer idValue;
if (resValue.isFramework()) {
idValue = Bridge.getResourceId(resValue.getResourceType(), resValue.getName());
} else {
idValue = mContext.getLayoutlibCallback().getResourceId(resValue.getResourceType(), resValue.getName());
}
if (idValue != null) {
return idValue;
}
Bridge.getLog().warning(LayoutLog.TAG_RESOURCES_RESOLVE, String.format("Unable to resolve id \"%1$s\" for attribute \"%2$s\"", value, mNames[index]), resValue);
return defValue;
}
use of com.android.ide.common.rendering.api.StyleResourceValue in project android_frameworks_base by ResurrectionRemix.
the class Resources_Theme_Delegate method setupResources.
// ---- private helper methods ----
private static boolean setupResources(Theme thisTheme) {
// Key is a space-separated list of theme ids applied that have been merged into the
// BridgeContext's theme to make thisTheme.
final ThemeKey key = thisTheme.getKey();
final int[] resId = key.mResId;
final boolean[] force = key.mForce;
boolean changed = false;
for (int i = 0, N = key.mCount; i < N; i++) {
StyleResourceValue style = resolveStyle(resId[i]);
if (style != null) {
RenderSessionImpl.getCurrentContext().getRenderResources().applyStyle(style, force[i]);
changed = true;
}
}
return changed;
}
use of com.android.ide.common.rendering.api.StyleResourceValue in project kotlin by JetBrains.
the class LintUtils method getStyleAttributes.
/**
* Looks up the resource values for the given attribute given a style. Note that
* this only looks project-level style values, it does not resume into the framework
* styles.
*/
@Nullable
public static List<ResourceValue> getStyleAttributes(@NonNull Project project, @NonNull LintClient client, @NonNull String styleUrl, @NonNull String namespace, @NonNull String attribute) {
if (!client.supportsProjectResources()) {
return null;
}
AbstractResourceRepository resources = client.getProjectResources(project, true);
if (resources == null) {
return null;
}
ResourceUrl style = ResourceUrl.parse(styleUrl);
if (style == null || style.framework) {
return null;
}
List<ResourceValue> result = null;
Queue<ResourceValue> queue = new ArrayDeque<ResourceValue>();
queue.add(new ResourceValue(style.type, style.name, false));
Set<String> seen = Sets.newHashSet();
int count = 0;
boolean isFrameworkAttribute = ANDROID_URI.equals(namespace);
while (count < 30 && !queue.isEmpty()) {
ResourceValue front = queue.remove();
String name = front.getName();
seen.add(name);
List<ResourceItem> items = resources.getResourceItem(front.getResourceType(), name);
if (items != null) {
for (ResourceItem item : items) {
ResourceValue rv = item.getResourceValue(false);
if (rv instanceof StyleResourceValue) {
StyleResourceValue srv = (StyleResourceValue) rv;
ItemResourceValue value = srv.getItem(attribute, isFrameworkAttribute);
if (value != null) {
if (result == null) {
result = Lists.newArrayList();
}
if (!result.contains(value)) {
result.add(value);
}
}
String parent = srv.getParentStyle();
if (parent != null && !parent.startsWith(ANDROID_PREFIX)) {
ResourceUrl p = ResourceUrl.parse(parent);
if (p != null && !p.framework && !seen.contains(p.name)) {
seen.add(p.name);
queue.add(new ResourceValue(ResourceType.STYLE, p.name, false));
}
}
int index = name.lastIndexOf('.');
if (index > 0) {
String parentName = name.substring(0, index);
if (!seen.contains(parentName)) {
seen.add(parentName);
queue.add(new ResourceValue(ResourceType.STYLE, parentName, false));
}
}
}
}
}
count++;
}
return result;
}
Aggregations