/** * Gets {@code NestedGenericType} annotation from object. * <p> * Looks at all object methods and returns first encountered annotation. * * @param object Object to deal with, not null * @return Annotation, may be null */ public static NestedGenericType getNestedGenericTypeAnnotation(Object object) { NestedGenericType result = null; Method[] methods = ClassReflection.getMethods(object.getClass()); // TODO - use type annotation, not method? for (Method m : methods) { Annotation[] annotations = m.getDeclaredAnnotations(); Annotation a = m.getDeclaredAnnotation(NestedGenericType.class); if (a != null) { result = a.getAnnotation(NestedGenericType.class); break; } } return result; }
public void invoke(JGameObject clickTarget) { for (Component component : clickTarget.getAllComponents()) { if (component.getClass().getName().equals(invokeComponent)) { Object[] parameters = args.toArray(new Object[args.size()]); Class[] parametersType = new Class[args.size()]; for (int x = 0; x < parameters.length; x++) { parametersType[x] = parameters[x].getClass(); } try { Method method = ClassReflection.getDeclaredMethod(component.getClass(), invokeMethod, parametersType); method.invoke(component, parameters); } catch (ReflectionException e) { e.printStackTrace(); } } } }
@Override public void printCommands () { for (Method m : getAllMethods()) { if (m.isPublic() && ConsoleUtils.canDisplayCommand(this, m)) { String s = ""; s += m.getName(); s += " : "; Class<?>[] params = m.getParameterTypes(); for (int i = 0; i < params.length; i++) { s += params[i].getSimpleName(); if (i < params.length - 1) { s += ", "; } } log(s); } } }
/** Does the actual processing of found methods. * * @param component owner of the methods. * @param methods present in one of superclasses of the component. * @param context used to resolve dependencies. * @param contextDestroyer used to register destruction callbacks. */ @SuppressWarnings({ "rawtypes", "unchecked" }) // Using correct types, but wildcards fail to see that. private void processMethods(final Object component, final Method[] methods, final Context context, final ContextDestroyer contextDestroyer) { for (final Method method : methods) { final com.badlogic.gdx.utils.reflect.Annotation[] annotations = getAnnotations(method); if (annotations == null || annotations.length == 0) { continue; } for (final com.badlogic.gdx.utils.reflect.Annotation annotation : annotations) { if (methodProcessors.containsKey(annotation.getAnnotationType())) { for (final AnnotationProcessor processor : methodProcessors.get(annotation.getAnnotationType())) { processor.processMethod(method, annotation.getAnnotation(annotation.getAnnotationType()), component, context, this, contextDestroyer); } } } } }
/** @param actionContainer action container that might contain the referenced method. * @param actionId name of the requested action. * @param forActor will be used as potential action argument. * @return actor consumer constructed with container's method (or field) or null if action not found. */ protected ActorConsumer<?, ?> extractActionFromContainer(final ActionContainerWrapper actionContainer, final String actionId, final Object forActor) { Method method = actionContainer.getNamedMethod(actionId); if (method == null && Lml.EXTRACT_UNANNOTATED_METHODS) { method = findUnnamedMethod(actionContainer, actionId, forActor); } if (method != null) { return new MethodActorConsumer(method, actionContainer.getActionContainer()); } else if (Lml.EXTRACT_FIELDS_AS_METHODS) { Field field = actionContainer.getNamedField(actionId); if (field == null && Lml.EXTRACT_UNANNOTATED_METHODS) { field = actionContainer.getField(actionId); } if (field != null) { return new FieldActorConsumer(field, actionContainer.getActionContainer()); } } return null; }
/** @param method will be inspected. * @return modifiers representing the method state. */ public static int getModifiers(final Method method) { int modifiers = 0; if (method.isAbstract()) { modifiers |= ABSTRACT; } if (method.isFinal()) { modifiers |= FINAL; } if (method.isNative()) { modifiers |= NATIVE; } if (method.isPrivate()) { modifiers |= PRIVATE; } if (method.isProtected()) { modifiers |= PROTECTED; } if (method.isPublic()) { modifiers |= PUBLIC; } if (method.isStatic()) { modifiers |= STATIC; } return modifiers; }
/** * Searches for the given method with the given class. If none is found, it looks for fitting methods * with the classe's interfaces and superclasses recursively. * @param methodName * @param clazz * @return */ private Method searchMethod(String methodName, Class<?> clazz, Class<?> source) { Method m = null; try { m = ClassReflection.getMethod(source, methodName, clazz); } catch (ReflectionException e) { try { if (methodName.contains("setCoordinates")) { // Special case m = ClassReflection.getMethod(source, methodName, IBodyCoordinates.class); } } catch (ReflectionException e1) { Logger.error(e1); } } return m; }
@Override public void doneLoading(AssetManager manager) { super.doneLoading(manager); // Set static coordinates to position coordinates.getEquatorialCartesianCoordinates(null, pos); // Initialize transform if (transformName != null) { Class<Coordinates> c = Coordinates.class; try { Method m = ClassReflection.getMethod(c, transformName); Matrix4d trf = (Matrix4d) m.invoke(null); coordinateSystem = new Matrix4(); trf.putIn(coordinateSystem); } catch (ReflectionException e) { Logger.error(this.getClass().getName(), "Error getting/invoking method Coordinates." + transformName + "()"); } } else { // Equatorial, nothing } // Model mc.doneLoading(manager, localTransform, null); }
public void setTransformName(String transformName) { this.transformName = transformName; if (transformName != null) { Class<Coordinates> c = Coordinates.class; try { Method m = ClassReflection.getMethod(c, transformName); Matrix4d transform = (Matrix4d) m.invoke(null); trf = new Matrix4d(transform); } catch (ReflectionException e) { Logger.error(this.getClass().getName(), "Error getting/invoking method Coordinates." + transformName + "()"); } } else { // Equatorial, nothing } }
@SuppressWarnings("static-access") @Before public void setup() { Gdx.app = Mockito.mock(HeadlessApplication.class); when(Gdx.app.getPreferences(anyString())).thenReturn(new PreferencesStub()); config = new TwitterConfig(); PowerMockito.mockStatic(ClassReflection.class); classReflectionMock = Mockito.mock(ClassReflection.class); PowerMockito.mockStatic(Field.class); fieldMock = Mockito.mock(Field.class); PowerMockito.mockStatic(Constructor.class); constructorMock = Mockito.mock(Constructor.class); PowerMockito.mockStatic(Method.class); methodMock = Mockito.mock(Method.class); activityStub = new ActivityStub(); twitterAPIStub = new TwitterAPIStub(config); gdxStub = new GdxStub(); supportFragmentStub = new SupportFragmentStub(); fragmentStub = new FragmentStub(); gdxLifecycleListenerStub = new GdxLifecycleListenerStub(); try { Mockito.when(classReflectionMock.forName("com.badlogic.gdx.Gdx")).thenReturn(gdxStub.getClass()); Mockito.when(classReflectionMock.getField(gdxStub.getClass(), "app")).thenReturn(fieldMock); Mockito.when(fieldMock.get(null)).thenReturn(Gdx.app); } catch (ReflectionException e) { } }
private void androidPremocking() { Application mockApplication = mock(Application.class); when(mockApplication.getType()).thenReturn(Application.ApplicationType.Android); Gdx.app = mockApplication; try { mockConstructor = PowerMockito.mock(Constructor.class); mockFacebook = mock(AndroidGDXFacebook.class); mockField = mock(Field.class); mockObject = mock(Object.class); mockMethod = mock(Method.class); when(ClassReflection.forName(GDXFacebookVars.CLASSNAME_ANDROID)).thenReturn(AndroidGDXFacebook.class); when(ClassReflection.getConstructor(AndroidGDXFacebook.class, GDXFacebookConfig.class)).thenReturn(mockConstructor); when(mockConstructor.newInstance(anyObject())).thenReturn(mockFacebook); when(ClassReflection.forName("com.badlogic.gdx.Gdx")).thenReturn(Gdx.class); when(ClassReflection.getField(Gdx.class, "app")).thenReturn(mockField); when(mockField.get(null)).thenReturn(mockObject); when(ClassReflection.forName("com.badlogic.gdx.backends.android.AndroidEventListener")).thenReturn(AndroidEventListener.class); when(ClassReflection.forName("android.app.Activity")).thenReturn(Activity.class); } catch (ReflectionException e) { e.printStackTrace(); } }
/** Utility method that allows to extract actual annotation from method, bypassing LibGDX annotation wrapper. * Returns null if annotation is not present. * * @param method method that might be annotated. * @param annotationType class of the annotation. * @return an instance of the annotation if the method is annotated or null if not. */ public static <Type extends Annotation> Type getAnnotation(final Method method, final Class<Type> annotationType) { if (isAnnotationPresent(method, annotationType)) { return method.getDeclaredAnnotation(annotationType).getAnnotation(annotationType); } return null; }
/** @param method will be set accessible and invoked. * @param methodOwner will have the method invoked. Can be null (static methods). * @param resultType result will be casted to this type. * @param arguments method arguments. * @return result of method invocation. * @throws ReflectionException when unable to invoke the method. */ @SuppressWarnings("unchecked") public static <ResultType> ResultType invokeMethod(final Method method, final Object methodOwner, final Class<ResultType> resultType, final Object... arguments) throws ReflectionException { method.setAccessible(true); return (ResultType) method.invoke(methodOwner, arguments); }
private ArrayList<Method> getAllMethods () { ArrayList<Method> methods = new ArrayList<Method>(); Class c = exec.getClass(); while (c != Object.class) { Collections.addAll(methods, ClassReflection.getDeclaredMethods(c)); c = c.getSuperclass(); } return methods; }
public void set (CommandExecutor ce, String s) { reset(); setString = s.toLowerCase(); Array<Method> methods = getAllMethods(ce); for (Method m : methods) { String name = m.getName(); if (name.toLowerCase().startsWith(setString) && ConsoleUtils.canDisplayCommand(ce.console, m)) { possibleCommands.add(name); } } iterator = new ObjectSetIterator<>(possibleCommands); }
/** Scans class tree of component to process all its methods. * * @param component all methods of its class tree will be processed. * @param context used to resolve dependencies. * @param contextDestroyer used to register destruction callbacks. */ private void processMethods(final Object component, final Context context, final ContextDestroyer contextDestroyer) { Class<?> componentClass = component.getClass(); while (componentClass != null && !componentClass.equals(Object.class)) { final Method[] methods = ClassReflection.getDeclaredMethods(componentClass); if (methods != null && methods.length > 0) { processMethods(component, methods, context, contextDestroyer); } componentClass = componentClass.getSuperclass(); } }
/** @param method will return an array of its annotations. * @return array of annotations or null. GWT utility. */ private static com.badlogic.gdx.utils.reflect.Annotation[] getAnnotations(final Method method) { try { return method.getDeclaredAnnotations(); } catch (final Exception exception) { Exceptions.ignore(exception); return null; } }
public ReflectionEventListener(final Method method, final Object methodOwner, final Context context, final boolean removeAfterInvocation, final boolean strict) { super(method, methodOwner, getParameters(method, context)); this.removeAfterInvocation = removeAfterInvocation; this.strict = strict; providers = getProviders(method, context); }
private static Object[] getParameters(final Method method, final Context context) { final Class<?>[] parameterTypes = method.getParameterTypes(); if (parameterTypes == null || parameterTypes.length == 0) { return Strings.EMPTY_ARRAY; } final Object[] parameters = new Object[parameterTypes.length]; for (int index = 0, length = parameterTypes.length; index < length; index++) { final Class<?> parameterType = parameterTypes[index]; if (context.isPresent(parameterType)) { parameters[index] = context.getComponent(parameterType); } } return parameters; }
private static ObjectProvider<?>[] getProviders(final Method method, final Context context) { final Class<?>[] parameterTypes = method.getParameterTypes(); if (parameterTypes == null || parameterTypes.length == 0) { return new ObjectProvider<?>[0]; } final ObjectProvider<?>[] providers = new ObjectProvider<?>[parameterTypes.length]; for (int index = 0, length = parameterTypes.length; index < length; index++) { final Class<?> parameterType = parameterTypes[index]; if (context.isProviderPresentFor(parameterType)) { providers[index] = context.getProvider(parameterType); } } return providers; }
public ReflectionMessageListener(final Method method, final Object methodOwner, final Context context, final boolean removeAfterInvocation, final boolean strict) { super(method, methodOwner, getParameters(method, context)); this.removeAfterInvocation = removeAfterInvocation; this.strict = strict; providers = getProviders(method, context); }
/** @param component will have its methods in class tree extracted. * @param context will be used to resolve method dependencies. */ protected void extractProviderMethods(final Object component, final Context context) { Class<?> componentClass = component.getClass(); while (componentClass != null && !componentClass.equals(Object.class)) { final Method[] methods = ClassReflection.getDeclaredMethods(componentClass); if (methods != null && methods.length > 0) { convertToProviders(component, methods, context); } componentClass = componentClass.getSuperclass(); } }
/** @param component is the owner of the methods. * @param methods will be converted to dependency providers and added to context. * @param context will contain the providers. Used to resolve methods' dependencies. */ protected void convertToProviders(final Object component, final Method[] methods, final Context context) { for (final Method method : methods) { final Class<?> returnType = method.getReturnType(); if (Annotations.isNotVoid(returnType)) { // Not null, void or Void. context.addProvider(new ReflectionDependencyProvider(context, method, component)); } } }
@Override public void processMethod(final Method method, final MyCustomAnnotation annotation, final Object component, final Context context, final ContextInitializer initializer, final ContextDestroyer contextDestroyer) { // Invoking annotated method with ID from annotation as parameter: Object result = null; try { method.setAccessible(true); result = method.invoke(component, annotation.id()); } catch (final ReflectionException exception) { LOGGER.error(exception, "Unable to invoke method."); } LOGGER.info("{0} had method '{1}' annotated with @MyCustomAnnotation. Method invocation result: {2}.", component, method.getName(), result); }
protected <View> void invokeAnnotatedViewMethods(final View view, final Class<? extends Annotation> annotation) { Class<?> handledClass = view.getClass(); try { while (handledClass != null && !handledClass.equals(Object.class)) { for (final Method method : ClassReflection.getDeclaredMethods(handledClass)) { if (Reflection.isAnnotationPresent(method, annotation)) { invokeAnnotatedViewMethod(view, method); } } handledClass = handledClass.getSuperclass(); } } catch (final Exception exception) { throw new GdxRuntimeException("Unable to invoke method annotated with: " + annotation, exception); } }
protected <View> void invokeAnnotatedViewMethod(final View view, final Method method) throws ReflectionException { final Class<?>[] parameterTypes = method.getParameterTypes(); if (parameterTypes == null || parameterTypes.length == 0) { Reflection.invokeMethod(method, view, (Object[]) Strings.EMPTY_ARRAY); } else if (parameterTypes.length == 1 && LmlParser.class.equals(parameterTypes[0])) { Reflection.invokeMethod(method, view, new Object[] { this }); } else { throw new GdxRuntimeException( "Only no-arg or single-arg methods consuming LmlParser can be annotated. Found invalid args on annotated method: " + method); } }
/** @param actionContainer may contain the action with the passed ID, but it was not annotated and assigned to a * specific ID. * @param actionId name of the method. * @param forActor will search through its class tree to look for methods that might consume an argument of this * type. Can be null - will look only for no-arg method. * @return method with the selected name or null if none found. */ protected Method findUnnamedMethod(final ActionContainerWrapper actionContainer, final String actionId, final Object forActor) { Method method = null; Class<?> parameterType = forActor == null ? null : forActor.getClass(); while (method == null) { if (parameterType == null) { method = actionContainer.getMethod(actionId, null); break; } method = actionContainer.getMethod(actionId, parameterType); parameterType = parameterType.getSuperclass(); } return method; }
public MethodActorConsumer(final Method method, final Object methodOwner) { if (method == null || methodOwner == null) { throw new IllegalArgumentException( "Method actor consumer has to wrap around an existing method and its owner."); } this.method = method; this.methodOwner = methodOwner; final Class<?>[] parameters = method.getParameterTypes(); if (parameters == null || parameters.length == 0) { arguments = LmlUtilities.EMPTY_ARRAY; } else { arguments = new Object[1]; } }
private void mapClassMethods(final Class<?> containerClass) { for (final Method method : ClassReflection.getDeclaredMethods(containerClass)) { final LmlAction actionData = Reflection.getAnnotation(method, LmlAction.class); if (actionData != null) { final String[] ids = actionData.value(); if (ids.length > 0) { for (final String actionId : ids) { annotatedMethods.put(actionId, method); } } else { annotatedMethods.put(method.getName(), method); } } } }
/** @param methodName name of the possibly contained method. * @param parameterClass class of the expected parameter. Optional. * @return method with passed name and one or zero parameters. Might be null. */ public Method getMethod(final String methodName, final Class<?> parameterClass) { Class<?> containerClass = actionContainer.getClass(); while (containerClass != null) { try { // If this does not throw an exception, the method is found. Null check is not needed. return getDeclaredMethod(containerClass, methodName, parameterClass); } catch (final Exception exception) { Exceptions.ignore(exception); // Expected. Method unavailable. } containerClass = containerClass.getSuperclass(); } return null; }
private static Method getDeclaredMethod(final Class<?> containerClass, final String methodName, final Class<?> parameterClass) throws ReflectionException { if (parameterClass == null) { return ClassReflection.getDeclaredMethod(containerClass, methodName); } return ClassReflection.getDeclaredMethod(containerClass, methodName, parameterClass); }
@Override protected void processFactory(final Object factory) { // Registering public methods as providers: for (final Method method : ClassReflection.getMethods(factory.getClass())) { if (isValidFactoryMethod(method)) { processProvider(newFactoryMethodWrapper(factory, method)); } } }
/** @param method cannot be synthetic, return void, have a forbidden name or have any filtered modifiers. * @return true if the method is valid and should be converted to a provider. */ protected boolean isValidFactoryMethod(final Method method) { final int modifiers = Modifier.getModifiers(method); return (modifiers & getMethodsIgnoreFilter()) == 0 && modifiers != getMethodsIgnoreSignature() && method.getReturnType() != void.class && method.getReturnType() != Void.class && !FORBIDDEN_METHOD_NAMES.contains(method.getName()); }
/** @param context parent context. * @param owner instance of the class with the method. * @param method will be wrapped and converted into a provider. */ public ReflectionProvider(final Context context, final Object owner, final Method method) { this.context = context; this.owner = owner; this.method = method; type = method.getReturnType(); parameterTypes = method.getParameterTypes(); parameters = parameterTypes.length == 0 ? Providers.EMPTY_ARRAY : new Object[parameterTypes.length]; name = Providers.getName(method); isDefault = owner instanceof Default; methodMember = new MethodMember(method); }