Loading entry based on dynamic route
I think it's because you're trying to cram too much into your entry variable.  For one, .slug() is going to return an entry with that slug, so I think that's a bit of a full stop.  For two, .descendantOf() accepts an EntryModal object, but you're feeding it a uri/slug (ie. name-of-artist).

Try something like this:

{% set artistEntry = craft.entries.slug(artistParent).first %}
{% set projectEntry = craft.entries.descendantOf(artistEntry).first %}


Keep in mind that .descendantOf() only works with structures (not channels), so I'm assuming that's what you're working with. Also, you may need to specify how far down the lineage to go with .descendantDist().