Instead of using UV coordinates you can use the Object coordinates of an Empty. In this way, the position of the pupil is controlled by the empty (you should Parent the empty to the eye so that it stays in place as the character moves) and the shape remains undistorted despite the geometry. This can be achieved as follows :
Here the Texture Coordinate's Object socket is used with the Object set to the Empty. This means that each point on the surface is handles in coordinates in relation to the specified object (the Empty) instead of your mesh coordinates.
The Vector Math node set to Multiply is set to mask out the Z coordinate and the following Vector Math set to Distance returns the distance from the centre. The distance is passed into the Color Ramp to produce the eye pattern based on the distance from the centre. If need be you can scale the eye texture by changing the X and Y multipliers in the Multiply node or by scaling the Empty itself.
Moving and rotating the Empty will move the texture, with it always aligned with the empty's Z-axis (although you can pick a different axis by changing which channel is multiplied by zero in the Multiply node).
To use an image texture instead of generating the eye from the distance from the centre, you can use something like the following :
Here the UV coordinates are manipulated using a Vector node to map the centre by 0.5 in each of the X and Y directions. This is to centre the image onto the empty (otherwise it will correspond to the top-left coordinate since that is the 'origin' of the image texture space). The Mix node uses the image Alpha to fill in the surrounding space around the texture. Note also that the Image Texture node is set to Clip so as to have only a single image.
As an aside, the first example (using the distance from the centre) uses nodes that were introduced relatively recently and aren't available at some earlier versions of Blender - in particular the Multiply and Distance modes of the Vector Math node. While the new nodes are very convenient, there are other ways to achieve the same thing - but you have to perform the underlying maths manually rather than relying on the convenient new node functions.
For example, you can achieve the same effect at Blender 2.79 using the following nodes :
Here the Separate XYZ uses only the X and Y coordinates - effectively the same as multiplying Z by zero - while the Power Maths node (raising to the power of 2), the Add, the Power (to the power of 0.5) calculates the distance using Pythagoras (sqrt(x^2 + y^2)
). The newer nodes offer a more convenient way by hiding the underlying maths.
Using your example Blend file I imported the material, images and meshes, re-located Empty.001 to near the surface and rotated it 90 degrees so its Z-axis pointed to the surface and scaled to size and produced the following result :