private DisplayLayerData GetDisplayData(int[] layerIdx)
        {
            if (importDisplay == null || layerIdx == null)
            {
                return(null);
            }

            DisplayLayerData currentLayer = importDisplay;

            foreach (int idx in layerIdx)
            {
                if (idx < 0 || idx >= currentLayer.Childs.Count)
                {
                    return(null);
                }
                currentLayer = currentLayer.Childs[idx];
            }
            return(currentLayer);
        }
        public static void BuildImportLayerData(Object file, ImportUserData importSettings,
                                                Action <ImportLayerData, DisplayLayerData> callback)
        {
            string filepath = GetPsdFilepath(file);

            if (string.IsNullOrEmpty(filepath))
            {
                if (callback != null)
                {
                    callback(null, null);
                }
                return;
            }

            using (PsdDocument psd = PsdDocument.Create(filepath))
            {
                ImportLayerData docImportData = new ImportLayerData()
                {
                    name    = DOC_ROOT,
                    indexId = new int[] { -1 },
                    Childs  = new List <ImportLayerData>()
                };
                DisplayLayerData docDisplayData = new DisplayLayerData()
                {
                    indexId = new int[] { -1 },
                    Childs  = new List <DisplayLayerData>()
                };

                EditorCoroutineRunner.StartCoroutine(
                    ParseLayers(psd.Childs, false,
                                onLayer: (layer, indexId) =>
                {
                    // Walk down the index id to get the parent layers
                    // and build the full path
                    string fullPath                = "";
                    ImportLayerData parentLayer    = docImportData;
                    DisplayLayerData parentDisplay = docDisplayData;
                    if (indexId.Length > 1)
                    {
                        for (int idIdx = 0; idIdx < indexId.Length - 1; idIdx++)
                        {
                            int idx       = indexId[idIdx];
                            parentLayer   = parentLayer.Childs[idx];
                            parentDisplay = parentDisplay.Childs[idx];

                            if (string.IsNullOrEmpty(fullPath) == false)
                            {
                                fullPath += "/";
                            }
                            fullPath += parentLayer.name;
                        }
                    }

                    if (string.IsNullOrEmpty(fullPath) == false)
                    {
                        fullPath += "/";
                    }
                    fullPath += layer.Name;

                    ImportLayerData layerImportData = new ImportLayerData()
                    {
                        name        = layer.Name,
                        path        = fullPath,
                        indexId     = indexId,
                        import      = layer.IsVisible,
                        useDefaults = true,
                        Alignment   = importSettings.DefaultAlignment,
                        Pivot       = importSettings.DefaultPivot,
                        ScaleFactor = importSettings.ScaleFactor,
                        Childs      = new List <ImportLayerData>()
                    };

                    DisplayLayerData layerDisplayData = new DisplayLayerData()
                    {
                        indexId   = indexId,
                        isVisible = layer.IsVisible,
                        isGroup   = layer.Childs.Length > 0,
                        isOpen    = layer.IsFolderOpen
                    };

                    int layerIdx = indexId[indexId.Length - 1];

                    int maxLayers = layerIdx + 1;
                    while (parentLayer.Childs.Count < maxLayers)
                    {
                        parentLayer.Childs.Add(null);
                    }

                    parentLayer.Childs[layerIdx] = layerImportData;

                    while (parentDisplay.Childs.Count < maxLayers)
                    {
                        parentDisplay.Childs.Add(null);
                    }

                    parentDisplay.Childs[layerIdx] = layerDisplayData;
                },
                                onComplete: () =>
                {
                    if (callback != null)
                    {
                        callback(docImportData, docDisplayData);
                    }
                })
                    );
            }
        }
        private void DrawLayerEntry(ImportLayerData layer, DisplayLayerData display)
        {
            bool     isGroup    = display.isGroup;
            bool     isSelected = quickSelect.Contains(layer.indexId);
            GUIStyle entryStyle = isSelected ? styleLayerSelected : styleLayerEntry;

            using (new GUILayout.HorizontalScope(entryStyle, layerHeight))
            {
                Rect rEntry = GUILayoutUtility.GetRect(rTableSize.x, rTableSize.x, rTableSize.y, rTableSize.y);

                Rect rToggle = new Rect(rImportToggle);
                Rect rVis    = new Rect(rVisible);
                Rect rLayer  = new Rect(rLayerDisplay);
                Rect rPiv    = new Rect(rPivot);
                Rect rScale  = new Rect(rScaling);
                Rect rReset  = new Rect(rMakeDefault);
                rToggle.y += rEntry.y;
                rVis.y    += rEntry.y;
                rLayer.y  += rEntry.y;
                rPiv.y    += rEntry.y;
                rScale.y  += rEntry.y;
                rReset.y  += rEntry.y;

                bool parentWillImport = ParentWillImport(layer.indexId);

                using (new EditorGUI.DisabledScope(parentWillImport == false))
                {
                    var displayImport = layer.import && parentWillImport;

                    EditorGUI.BeginChangeCheck();
                    displayImport = GUI.Toggle(rToggle, displayImport, GUIContent.none);

                    if (EditorGUI.EndChangeCheck() && parentWillImport)
                    {
                        layer.import = displayImport;
                        CollateImportList();
                        quickSelect.Clear();
                        selectionCount    = 0;
                        lastSelectedLayer = null;
                    }
                }

                using (new EditorGUI.DisabledScope(true))
                {
                    var visStyle = display.isVisible ? styleVisOn : styleVisOff;
                    GUI.Label(rVis, GUIContent.none, visStyle);
                }

                rLayer.xMin += indentLevel * indentWidth;

                GUIContent layerContent = new GUIContent()
                {
                    image = isGroup ? icnFolder : icnTexture,
                    text  = layer.name
                };

                if (isGroup)
                {
                    float min, max;
                    EditorStyles.popup.CalcMinMaxWidth(layerContent, out min, out max);
                    rLayer.width   = min;
                    display.isOpen = EditorGUI.Foldout(rLayer, display.isOpen, layerContent);
                }
                else
                {
                    EditorGUI.LabelField(rLayer, layerContent);

                    if (isAdvancedMode)
                    {
                        DrawLayerAdvanced(layer, rPiv, rScale, rReset);
                    }
                }
            }

            Rect layerRect = GUILayoutUtility.GetLastRect();

            layerRect.xMin += 40;
            layerRectLookup.Add(layer.indexId, layerRect);
            layerEntryYMax = Mathf.Max(layerEntryYMax, layerRect.yMax);
        }
        public void OpenFile(Object fileObject)
        {
            if (isOpeningFile)
            {
                return;
            }

            importFile    = null;
            importPath    = string.Empty;
            importPreview = null;
            importPPU     = 100;

            importSettings = new ImportUserData()
            {
                DocAlignment = SpriteAlignment.Center
            };
            importDisplay = null;

            selectionCount = 0;
            quickSelect.Clear();
            lastSelectedLayer = null;

            var filePath = AssetDatabase.GetAssetPath(fileObject);

            if (filePath.ToLower().EndsWith(".psd") == false)
            {
                return;
            }

            importFile    = fileObject;
            importPath    = filePath;
            importPreview = AssetDatabase.LoadAssetAtPath <Texture2D>(importPath);

            // Read the texture import settings of the asset file
            TextureImporter         textureImporter     = (TextureImporter)AssetImporter.GetAtPath(importPath);
            TextureImporterSettings unityImportSettings = new TextureImporterSettings();

            textureImporter.ReadTextureSettings(unityImportSettings);

            importPPU = unityImportSettings.spritePixelsPerUnit;

            // Attempt to deserialize
            string json           = textureImporter.userData;
            bool   didGetUserData = false;

            if (string.IsNullOrEmpty(json) == false)
            {
                fsData data        = fsJsonParser.Parse(json);
                object deserialObj = null;
                if (serializer.TryDeserialize(data, typeImportUserData, ref deserialObj)
                    .AssertSuccessWithoutWarnings()
                    .Succeeded)
                {
                    importSettings = (ImportUserData)deserialObj;
                    if (importSettings == null)
                    {
                        importSettings = new ImportUserData();
                    }
                    else
                    {
                        didGetUserData = true;
                    }
                }
            }

            if (didGetUserData)
            {
                settingsChanged = false;
            }
            else
            {
                settingsChanged    = true;
                showImportSettings = true;
            }

            isOpeningFile = true;
            PsdImporter.BuildImportLayerData(importFile, importSettings, (layerData, displayData) =>
            {
                importSettings.DocRoot = ResolveData(importSettings.DocRoot, layerData);

                importDisplay = displayData;
                isOpeningFile = false;
                CollateImportList();
                Repaint();
            });
        }