private void StartPicking(SerializedProperty property, FieldInfo fieldInfo, Type pickType)
        {
            PickCallbackAttribute attribute = GetAttribute <PickCallbackAttribute>(fieldInfo);
            string callback = attribute == null ? null : attribute.CallbackName;

            StartPicking(property, pickType, callback);
        }
        protected void OnGUI(
            Rect position, SerializedProperty property, GUIContent label,
            DefaultFieldDrawer defaultFieldDrawer = null)
        {
            Type pickType = IsCollection(fieldInfo.FieldType)
                ? GetCollectionElementType(fieldInfo.FieldType)
                : fieldInfo.FieldType;

            Type pickTypePacked = pickType;

            // Unpack it. If it's an interface reference, then the pick type is actually the
            // interface type. Separate from the array check because it can ALSO be an array.
            pickType = GetPickType(pickType);

            bool isValid = HasTransform(pickTypePacked) &&
                           !IsPrefab(property.serializedObject.targetObject);

            if (!isValid)
            {
                if (defaultFieldDrawer != null)
                {
                    defaultFieldDrawer(position, property, label);
                }
                else
                {
                    EditorGUI.PropertyField(position, property, label, true);
                }
                return;
            }

            float width = 18;
            float space = 4;

            Rect positionField = position;

            positionField.xMax -= width + space - 4;

            Object previousValue = property.objectReferenceValue;

            // Draw the field itself. Either use the drawer that was supplied or do a generic one.
            EditorGUI.BeginChangeCheck();
            if (defaultFieldDrawer != null)
            {
                defaultFieldDrawer(positionField, property, label);
            }
            else
            {
                EditorGUI.PropertyField(positionField, property, label, true);
            }
            bool didManuallyAssignNewValue = EditorGUI.EndChangeCheck();

            Rect positionPicker = new Rect(
                positionField.xMax + space, positionField.yMin - 1, width, position.height);

            bool wasPicking = PropertyPicking == property ||
                              (PropertyPicking != null &&
                               PropertyPicking.serializedObject ==
                               property.serializedObject &&
                               PropertyPicking.propertyPath == property.propertyPath);

            GUIContent icon;

            if (wasPicking)
            {
                icon = buttonGuiContentActive;
            }
            else
            {
                icon = EditorGUIUtility.isProSkin ? buttonGuiContentPro : buttonGuiContentPersonal;
            }

            bool wantsToPick = GUI.Toggle(positionPicker, wasPicking, icon, ButtonStyle);

            // If we manually assigned a new value, try to fire the callback.
            if (didManuallyAssignNewValue)
            {
                Object currentValue = property.objectReferenceValue;

                PickCallbackAttribute attribute = GetAttribute <PickCallbackAttribute>(fieldInfo);

                if (attribute != null)
                {
                    string callback = attribute.CallbackName;

                    FireSceneViewPickerCallback(
                        property, callback, previousValue, currentValue);
                }
            }

            if (wasPicking && (!wantsToPick || didManuallyAssignNewValue))
            {
                StopPicking();
            }

            if (!wasPicking && wantsToPick)
            {
                StartPicking(property, fieldInfo, pickType);
            }
        }