You can pass it directly. A lot of it depends on how you structure your code, but if your Screen needs an instance of SpriteBatch to do work, give it that instance.
public Screen(Game game, SpriteBatch spriteBatch)
{
...
}
public PlayScreen(GameRoot game, SpriteBatch spriteBatch)
: base(game, spriteBatch)
{
...
}
// In some GameRoot object which has a SpriteBatch named mySpriteBatch
var playScreen = new PlayScreen(gameInstance, mySpriteBatch);
Same deal, give the screen an instance of viewport that it can use to do work. Constructor injection is fairly common and an easy way to get dependencies into your objects. Keep an eye out though… sometimes you find your constructors growing. If you think it’s starting to get unreasonable you can explore other options, such as using a dependency container. You can also pass dependencies in as method parameters, typically if they’re single use and not used anywhere except that method. Kinda one of those things you do by feel… at least for me. Others may have better ideas
The nice thing about dependency injection though is it makes your code much easier to unit test since you don’t need to worry about staging anything. Everything your object needs is given to it, it doesn’t have to get it from anywhere.