android如何获得所有可能的值的枚举自定义属性?

标签: Java Android
发布时间: 2017/3/19 18:47:46
注意事项: 本文中文内容可能为机器翻译,如要查看英文原文请点击上面连接.

假设我有一个自定义的属性 my_custom_enum ,我的意见︰

<attr name="my_custom_enum" format="enum">
    <enum name="first_value" value="751"/>
    <enum name="second_value" value="2222"/>
    <enum name="third_value" value="1241"/>
    <enum name="fourth_value" value="4"/>
</attr>

<declare-styleable name="CustomViewOne">
    <attr name="my_custom_enum"/>
</declare-styleable>

<declare-styleable name="CustomViewTwo">
    <attr name="my_custom_enum"/>
</declare-styleable>

有没有办法获得的代码在此枚举所有可能的值

换句话说︰

我想要的方式来获取值 751222212414 . names 这些价值观的好也会但不是强制性。

解决方法 1:

最终的解决方案是由pskink评论中建议︰ 解析 attrs.xml 和提取值自己。

有两个原因使它完全可以这样做︰

  1. 我需要这个单元测试 (要了解更多关于那,读我的谈话与pskink在下问题的评论)。
  2. 对名称/值不存储在任何地方。只有 ints 使用时使用 AttributeSet

这是最终的代码︰

public final class AttrsUtils {

    private static final String TAG_ATTR = "attr";
    private static final String TAG_ENUM = "enum";
    private static final String ATTRIBUTE_NAME = "name";
    private static final String ATTRIBUTE_FORMAT = "format";
    private static final String ATTRIBUTE_VALUE = "value";

    @CheckResult
    @NonNull
    public static Map<String, Integer> getEnumAttributeValues(String attrName)
            throws ParserConfigurationException, IOException, SAXException {
        final File attrsFile = new File("../app/src/main/res/values/attrs.xml");
        DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
        DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
        Document doc = dBuilder.parse(attrsFile);
        doc.getDocumentElement().normalize();

        Map<String, Integer> fontAttributes = new ArrayMap<>();

        NodeList nList = doc.getElementsByTagName(TAG_ATTR);
        for (int temp = 0; temp < nList.getLength(); temp++) {
            Node attrNode = nList.item(temp);
            if (attrNode.getNodeType() == Node.ELEMENT_NODE) {
                Element attrElement = (Element) attrNode;
                final String name = attrElement.getAttribute(ATTRIBUTE_NAME);
                if (!attrElement.hasAttribute(ATTRIBUTE_FORMAT) || !name.equals(attrName)) {
                    continue;
                }

                final NodeList enumNodeList = attrElement.getElementsByTagName(TAG_ENUM);
                for (int i = 0, size = enumNodeList.getLength(); i < size; ++i) {
                    final Node enumNode = enumNodeList.item(i);
                    if (enumNode.getNodeType() == Node.ELEMENT_NODE) {
                        Element enumElement = (Element) enumNode;
                        fontAttributes.put(
                                enumElement.getAttribute(ATTRIBUTE_NAME),
                                Integer.parseInt(enumElement.getAttribute(ATTRIBUTE_VALUE)));
                    }
                }
                break; // we already found the right attr, we can break the loop
            }
        }
        return fontAttributes;
    }

    // Suppress default constructor for noninstantiability
    private AttrsUtils() {
        throw new AssertionError();
    }
}

此方法返回 Mapname - value 表示具有的属性对 attrName


例如我在问题中写道,您将使用此方法像这样︰

Map<String, Integer> enumAttr = AttrsUtils.getEnumAttributeValues("my_custom_enum");
赞助商