Update
Just to clarify that: Some people might have the impression I'm saying AOP is something bad and should not be used. That's not what I'm saying! AOP is actually a great feature. I just say "Use it carefully". AOP will only cause problems if you mix up normal code and AOP for the same Aspect. In the example above, we have the Aspect of updating the values of a graphical object and painting the updated object. That is in fact a single aspect. Coding half of it as normal code and the other half of it as aspect is what adds the problem.
If you use AOP for a completely different aspect, e.g. for logging, you will not run into the anti-pattern problem. In that case a newbie to the project might wonder "Where do all these log messages come from? I don't see any log output in the code", but that is not a huge problem. Changes he makes to the program logic will hardly break the log facility and changes made to the log facility will hardly break his program logic - these aspects are totally separated. Using AOP for logging has the advantage that your program code can fully concentrate on doing whatever it should do and you still can have sophisticated logging, without having your code being cluttered up by hundreds of log messages everywhere. Also when new code is introduced, magically log messages will appear at the right time with the right content. The newbie programmer might not understand why they are there or where they came from, but since they will log the "right thing" at the "right time", he can just happily accept the fact that they are there and move on to something else.
So a good usage of AOP in my example would be to always log if any value has been updated via a set method. This will not create an anti-pattern and hardly ever be the cause of any problem.
One might say, if you can easily abuse AOP to create so many problems, it's a bad idea to use it all. However which technology can't be abused? You can abuse data encapsulation, you can abuse inheritance. Pretty much every useful programming technology can be abused. Consider a programming language so limited that it only contains features that can't be abused; a language where features can only be used as they were initially intended to be used. Such a language would be so limited that it's arguable if it can be even used for real world programming.