RowSelection DisplayRow(int rowId, PackageInfo package, bool isSelected)
        {
            // -- Extract the package information. --
            var title     = package.PackageName;
            var folder    = package.GetRelativePackageFolder();
            var separator = string.IsNullOrEmpty(folder) ? "" : "/";

            folder = "Assets" + separator + folder;
            var version       = package.PackageVersion;
            var isRootPackage = package.IsRootPackage;
            // -- Determine if mouse is hovering. --
            float y             = rowId * kRowHeight;
            var   mousePosition = Event.current.mousePosition + Event.current.delta;
            bool  isMouseOver   = false;

            if (mouseOverWindow)
            {
                if (mousePosition.y >= y && mousePosition.y < y + kRowHeight)
                {
                    isMouseOver = true;
                }
            }

            // -- Assume project is selected if mouse button is pressed. --
            var rowSelection = RowSelection.None;
            var e            = Event.current;

            if (isMouseOver && e.type == EventType.MouseDown && e.button == 0)
            {
                rowSelection = RowSelection.Project;
            }

            // -- Add separator line between project rows. --
            if (rowId != 0)
            {
                Handles.color = Color.grey;
                Handles.DrawLine(new Vector3(kSpacer, y), new Vector3(kWidth - kSpacer, y));
            }
            ourProjectTitleStyle.normal.textColor = isSelected ? ourSelectedColor : Color.black;

            // -- Show project title and version. --
            y += kSpacer;
            var titleContent = new GUIContent(title);
            var titleSize    = ourProjectTitleStyle.CalcSize(titleContent);
            var titleRect    = new Rect(kSpacer, y, kWidth, kRowHeight);

            GUI.Label(titleRect, titleContent, ourProjectTitleStyle);
            if (isMouseOver)
            {
                Handles.color = ourProjectTitleStyle.normal.textColor;
                var lineY = titleRect.y + 0.85f * titleSize.y;
                Handles.DrawLine(new Vector3(kSpacer, lineY), new Vector3(kSpacer + titleSize.x, lineY));
            }
            var versionContent = new GUIContent(version);
            var versionSize    = ourProjectTitleStyle.CalcSize(versionContent);
            var versionRect    = new Rect(kWidth - kSpacer - versionSize.x, y, versionSize.x, versionSize.y);

            GUI.Label(versionRect, versionContent, ourProjectTitleStyle);

            // -- Show option buttons. --
            if (!isRootPackage)
            {
                EditorGUI.BeginDisabledGroup(true);
                var settingRect = new Rect(kWidth - kSpacer - 300f, y, 100f - 0.5f * kSpacer, 34f);
                if (GUI.Button(settingRect, "Settings"))
                {
                    rowSelection = RowSelection.Settings;
                }
                EditorGUI.EndDisabledGroup();
                EditorGUI.BeginDisabledGroup(PackageController.HasChildPackage(package));
                var removeRect = new Rect(kWidth - kSpacer - 200f, y, 100f - 0.5f * kSpacer, 34f);
                if (GUI.Button(removeRect, "Remove"))
                {
                    rowSelection = RowSelection.Remove;
                }
                EditorGUI.EndDisabledGroup();
            }

            // -- Show project folder. --
            titleRect.y += ourProjectTitleStyle.fontSize + 0.25f * kSpacer;
            GUI.Label(titleRect, folder, ourProjectFolderStyle);

            return(rowSelection);
        }