Search in sources :

Example 36 with ResourceType

use of com.android.resources.ResourceType in project android by JetBrains.

the class ResourceFolderRepository method scanFileResourceFolder.

private void scanFileResourceFolder(@NotNull VirtualFile directory, ResourceFolderType folderType, String qualifiers, FolderConfiguration folderConfiguration) {
    List<ResourceType> resourceTypes = FolderTypeRelationship.getRelatedResourceTypes(folderType);
    assert resourceTypes.size() >= 1 : folderType;
    ResourceType type = resourceTypes.get(0);
    boolean idGeneratingFolder = FolderTypeRelationship.isIdGeneratingFolderType(folderType);
    ListMultimap<String, ResourceItem> map = getMap(type, true);
    for (VirtualFile file : directory.getChildren()) {
        if (file.isValid() && !file.isDirectory()) {
            FileType fileType = file.getFileType();
            boolean idGeneratingFile = idGeneratingFolder && fileType == StdFileTypes.XML;
            if (PsiProjectListener.isRelevantFileType(fileType) || folderType == ResourceFolderType.RAW) {
                scanFileResourceFile(qualifiers, folderType, folderConfiguration, type, idGeneratingFile, map, file);
            }
        // TODO: Else warn about files that aren't expected to be found here?
        }
    }
}
Also used : VirtualFile(com.intellij.openapi.vfs.VirtualFile) FileType(com.intellij.openapi.fileTypes.FileType) ResourceType(com.android.resources.ResourceType)

Example 37 with ResourceType

use of com.android.resources.ResourceType in project android by JetBrains.

the class ResourceFolderRepository method scanQueuedPsiResources.

/**
   * For resource files that failed when scanning with a VirtualFile, retry with PsiFile.
   */
private void scanQueuedPsiResources() {
    PsiManager psiManager = PsiManager.getInstance(myModule.getProject());
    for (PsiValueResourceQueueEntry valueResource : myInitialScanState.myPsiValueResourceQueue) {
        PsiFile file = psiManager.findFile(valueResource.file);
        if (file != null) {
            scanValueFileAsPsi(valueResource.qualifiers, file, valueResource.folderConfiguration);
        }
    }
    for (PsiFileResourceQueueEntry fileResource : myInitialScanState.myPsiFileResourceQueue) {
        PsiFile file = psiManager.findFile(fileResource.file);
        if (file != null) {
            List<ResourceType> resourceTypes = FolderTypeRelationship.getRelatedResourceTypes(fileResource.folderType);
            assert resourceTypes.size() >= 1 : fileResource.folderType;
            ResourceType type = resourceTypes.get(0);
            ListMultimap<String, ResourceItem> map = getMap(type, true);
            scanFileResourceFileAsPsi(fileResource.qualifiers, fileResource.folderType, fileResource.folderConfiguration, type, true, map, file);
        }
    }
}
Also used : ResourceType(com.android.resources.ResourceType)

Example 38 with ResourceType

use of com.android.resources.ResourceType in project android by JetBrains.

the class ResourceFolderRepository method rescanImmediately.

private void rescanImmediately(@NonNull final PsiFile psiFile, @NonNull final ResourceFolderType folderType) {
    if (!ApplicationManager.getApplication().isReadAccessAllowed()) {
        ApplicationManager.getApplication().runReadAction(new Runnable() {

            @Override
            public void run() {
                rescanImmediately(psiFile, folderType);
            }
        });
        return;
    }
    PsiFile file = psiFile;
    if (folderType == VALUES) {
        // For unit test tracking purposes only
        //noinspection AssignmentToStaticFieldFromInstanceMethod
        ourFullRescans++;
        // First delete out the previous items
        ResourceFile resourceFile = myResourceFiles.get(file.getVirtualFile());
        boolean removed = false;
        if (resourceFile != null) {
            for (ResourceItem item : resourceFile.getItems()) {
                // Will throw away file
                removed |= removeItems(resourceFile, item.getType(), item.getName(), false);
            }
            myResourceFiles.remove(file.getVirtualFile());
        }
        file = ensureValid(file);
        boolean added = false;
        if (file != null) {
            // Add items for this file
            PsiDirectory parent = file.getParent();
            // since we have a folder type
            assert parent != null;
            String dirName = parent.getName();
            PsiDirectory fileParent = psiFile.getParent();
            if (fileParent != null) {
                FolderConfiguration folderConfiguration = FolderConfiguration.getConfigForFolder(fileParent.getName());
                if (folderConfiguration != null) {
                    added = scanValueFileAsPsi(getQualifiers(dirName), file, folderConfiguration);
                }
            }
        }
        if (added || removed) {
            // TODO: Consider doing a deeper diff of the changes to the resource items
            // to determine if the removed and added items actually differ
            myGeneration = ourModificationCounter.incrementAndGet();
            invalidateItemCaches();
        }
    } else {
        ResourceFile resFile = myResourceFiles.get(file.getVirtualFile());
        // If the old file was a PsiResourceFile, we could try to update ID ResourceItems in place.
        if (resFile != null && resFile instanceof PsiResourceFile) {
            PsiResourceFile resourceFile = (PsiResourceFile) resFile;
            // in that case we may need to update the id's
            if (FolderTypeRelationship.isIdGeneratingFolderType(folderType) && file.getFileType() == StdFileTypes.XML) {
                // For unit test tracking purposes only
                //noinspection AssignmentToStaticFieldFromInstanceMethod
                ourFullRescans++;
                // We've already seen this resource, so no change in the ResourceItem for the
                // file itself (e.g. @layout/foo from layout-land/foo.xml). However, we may have
                // to update the id's:
                Set<String> idsBefore = Sets.newHashSet();
                Set<String> idsAfter = Sets.newHashSet();
                ListMultimap<String, ResourceItem> map = myItems.get(ResourceType.ID);
                if (map != null) {
                    List<ResourceItem> idItems = Lists.newArrayList();
                    for (ResourceItem item : resourceFile) {
                        if (item.getType() == ResourceType.ID) {
                            idsBefore.add(item.getName());
                            idItems.add(item);
                        }
                    }
                    for (String id : idsBefore) {
                        // Note that ResourceFile has a flat map (not a multimap) so it doesn't
                        // record all items (unlike the myItems map) so we need to remove the map
                        // items manually, can't just do map.remove(item.getName(), item)
                        List<ResourceItem> mapItems = map.get(id);
                        if (mapItems != null && !mapItems.isEmpty()) {
                            List<ResourceItem> toDelete = Lists.newArrayListWithExpectedSize(mapItems.size());
                            for (ResourceItem mapItem : mapItems) {
                                if (mapItem.getSource() == resourceFile) {
                                    toDelete.add(mapItem);
                                }
                            }
                            for (ResourceItem delete : toDelete) {
                                map.remove(delete.getName(), delete);
                            }
                        }
                    }
                    resourceFile.removeItems(idItems);
                }
                // Add items for this file
                List<ResourceItem> idItems = Lists.newArrayList();
                file = ensureValid(file);
                if (file != null) {
                    addIds(idItems, file);
                }
                if (!idItems.isEmpty()) {
                    resourceFile.addItems(idItems);
                    for (ResourceItem item : idItems) {
                        idsAfter.add(item.getName());
                    }
                }
                if (!idsBefore.equals(idsAfter)) {
                    myGeneration = ourModificationCounter.incrementAndGet();
                }
                scanDataBinding(resourceFile, myGeneration);
                // Identities may have changed even if the ids are the same, so update maps
                invalidateItemCaches(ResourceType.ID);
            }
        } else {
            // Remove old items first, if switching to Psi. Rescan below to add back, but with a possibly different multimap list order.
            boolean switchingToPsi = resFile != null && !(resFile instanceof PsiResourceFile);
            if (switchingToPsi) {
                removeItemsFromFile(resFile);
            }
            // For unit test tracking purposes only
            //noinspection AssignmentToStaticFieldFromInstanceMethod
            ourFullRescans++;
            PsiDirectory parent = file.getParent();
            // since we have a folder type
            assert parent != null;
            String dirName = parent.getName();
            List<ResourceType> resourceTypes = FolderTypeRelationship.getRelatedResourceTypes(folderType);
            assert resourceTypes.size() >= 1 : folderType;
            ResourceType type = resourceTypes.get(0);
            boolean idGeneratingFolder = FolderTypeRelationship.isIdGeneratingFolderType(folderType);
            ListMultimap<String, ResourceItem> map = getMap(type, true);
            file = ensureValid(file);
            if (file != null) {
                PsiDirectory fileParent = psiFile.getParent();
                if (fileParent != null) {
                    FolderConfiguration folderConfiguration = FolderConfiguration.getConfigForFolder(fileParent.getName());
                    if (folderConfiguration != null) {
                        boolean idGeneratingFile = idGeneratingFolder && file.getFileType() == StdFileTypes.XML;
                        scanFileResourceFileAsPsi(getQualifiers(dirName), folderType, folderConfiguration, type, idGeneratingFile, map, file);
                    }
                }
                myGeneration = ourModificationCounter.incrementAndGet();
                invalidateItemCaches();
            }
        }
    }
}
Also used : ResourceType(com.android.resources.ResourceType) FolderConfiguration(com.android.ide.common.resources.configuration.FolderConfiguration)

Example 39 with ResourceType

use of com.android.resources.ResourceType in project android by JetBrains.

the class AndroidDocumentationProvider method generateDoc.

@Override
public String generateDoc(PsiElement element, @Nullable PsiElement originalElement) {
    if (originalElement == null) {
        return null;
    }
    ResourceReferenceType referenceType = AndroidPsiUtils.getResourceReferenceType(originalElement);
    if (referenceType == ResourceReferenceType.NONE) {
        return null;
    }
    Module module = ModuleUtilCore.findModuleForPsiElement(originalElement);
    if (module == null) {
        return null;
    }
    ResourceType type = AndroidPsiUtils.getResourceType(originalElement);
    if (type == null) {
        return null;
    }
    String name = AndroidPsiUtils.getResourceName(originalElement);
    boolean isFrameworkResource = referenceType == ResourceReferenceType.FRAMEWORK;
    return AndroidJavaDocRenderer.render(module, type, name, isFrameworkResource);
}
Also used : ResourceReferenceType(com.android.tools.idea.AndroidPsiUtils.ResourceReferenceType) ResourceType(com.android.resources.ResourceType) Module(com.intellij.openapi.module.Module)

Example 40 with ResourceType

use of com.android.resources.ResourceType in project android by JetBrains.

the class ResourceValue method getErrorMessage.

@Nullable
public String getErrorMessage() {
    // resource url (it's missing a resource type, "null" is a Java keyword, etc)
    if ("null".equals(myResourceName) && myResourceType == null && myPrefix == '@') {
        return null;
    }
    if (myResourceName == null || myResourceName.isEmpty()) {
        if (myResourceType == null && (myPrefix == '@' || myPrefix == '?')) {
            return "Missing resource type";
        }
        return "Missing resource name";
    }
    ResourceType type;
    if (myResourceType == null) {
        if (myPrefix != '?') {
            if (myPrefix == '@' && myResourceName.indexOf('/') == -1) {
                return "Missing /";
            }
            return "Missing resource type";
        }
        type = ResourceType.ATTR;
    } else if (PLUS_ID.equals(myResourceType)) {
        type = ResourceType.ID;
    } else {
        type = ResourceType.getEnum(myResourceType);
        if (type == null) {
            return "Unknown resource type " + myResourceType;
        }
    }
    String name = myResourceName;
    if (FolderTypeRelationship.getRelatedFolders(type).contains(ResourceFolderType.VALUES)) {
        name = AndroidResourceUtil.getFieldNameByResourceName(name);
    }
    if (!AndroidUtils.isIdentifier(name)) {
        if (JavaLexer.isKeyword(name, LanguageLevel.JDK_1_5)) {
            return "Resource name cannot be a Java keyword (" + name + ")";
        }
        if (!Character.isJavaIdentifierStart(name.charAt(0))) {
            return "The resource name must begin with a character";
        }
        for (int i = 1, n = name.length(); i < n; i++) {
            char c = name.charAt(i);
            if (!Character.isJavaIdentifierPart(c)) {
                return String.format("'%1$c' is not a valid resource name character", c);
            }
        }
        return "Resource name '" + name + "' must be a valid Java identifier";
    }
    return null;
}
Also used : ResourceType(com.android.resources.ResourceType) Nullable(org.jetbrains.annotations.Nullable)

Aggregations

ResourceType (com.android.resources.ResourceType)137 ResourceValue (com.android.ide.common.rendering.api.ResourceValue)31 NotNull (org.jetbrains.annotations.NotNull)16 Field (java.lang.reflect.Field)13 StyleResourceValue (com.android.ide.common.rendering.api.StyleResourceValue)12 BridgeContext (com.android.layoutlib.bridge.android.BridgeContext)11 VirtualFile (com.intellij.openapi.vfs.VirtualFile)10 Map (java.util.Map)10 Nullable (org.jetbrains.annotations.Nullable)10 Nullable (com.android.annotations.Nullable)8 ResourceFolderType (com.android.resources.ResourceFolderType)8 File (java.io.File)8 EnumMap (java.util.EnumMap)7 AndroidFacet (org.jetbrains.android.facet.AndroidFacet)7 Context (android.content.Context)6 View (android.view.View)6 AbsListView (android.widget.AbsListView)6 AdapterView (android.widget.AdapterView)6 ExpandableListView (android.widget.ExpandableListView)6 FrameLayout (android.widget.FrameLayout)6