Override TPL path dynamically
Use an extension's templates dir

Creating a simple extension via civix provides a templates/ directory in the extension. This is searched before the default templates, so you can intercept and provide your own.

If that doesn't go far enough &amp; you want to dynamically select a template (eg replace Form.php, but only when foo=123), these options are available:

Use CiviCRM's hook_civicrm_alterTemplateFile()

Alters template files, based on the form &amp; form data. This is something you'd do in an extension or CMS module. (Function signature refers to $form, I'm not sure what this will mean if you're rendering a page.)

Nest templates

Copy the default template Foo.tpl to your custom (or extension) template dir as Foo-default.tpl and Foo-123.tpl, create a wrapper Foo.tpl which uses Smarty to insert the correct template based on your criteria.

This last method can be done without creating a custom extension.