Assets and Network Images
In a Flutter application, we can work with local images (in the assets folder), and/or network images (url-based).
Let's start with working with local images:
Create a folder, assets, in the root of the app. Then, create images folder in that created folder.
Next, go to pubspec.yaml in the root and then uncomment the block for assets: then modify it so that it can be like this:
flutter:
  # ...
  assets:
    - assets/images/
  # ...
Ensure the indentation of the modified block in the yaml file is space-specific as the one above or it will not work.

Next, add photos you will use, format-supported, in the images folder. For my case, I used sample.png

Note: If it does not pick the image, you might be forced to reinstall the app.
import 'package:flutter/material.dart';

void main() {
  runApp(const MaterialApp(debugShowCheckedModeBanner: false, home: MyApp()));
}

class MyApp extends StatelessWidget {
  const MyApp({super.key});
  @override
  Widget build(BuildContext context) {
    return const SafeArea(
      child:
          Scaffold(
            body: Image(
              image: AssetImage('assets/images/sample.png') // AssetImage
            ) // Image
            /* OR
            * body: Image.asset("assets/images/sample.png")),
            */
            ), // Scaffold
    ); // SafeArea
  }
}
Now, in order to use url-based images, the codebase will be modified to use NetworkImage class as below:
// ...
return const SafeArea(
  child: Scaffold(
      body: Image(
        image: NetworkImage("https://picsum.photos/250?image=9"),
  ) // Image
  /* OR
  * body: Image.network("https://picsum.photos/250?image=9")
  */
  ), // Scaffold
); // SafeArea
// ...
Modifying image bounds
If, for instance, we'd want an image with rounded corners, we'll use the ClipRRect class as below:
// ...
return SafeArea(
  child: Scaffold(
    body: ClipRRect(
      borderRadius: BorderRadius.circular(20.0),
      child: Image.asset("assets/images/sample.png"))),
);
// ...
To get a fully rounded image, the class CircleAvatar wraps the image as below:
// ...
return const SafeArea(
  child: Scaffold(
    body: CircleAvatar(
      radius: 80.0,
      backgroundImage: AssetImage("assets/images/sample.png"))),
);
// ...
Now let's talk about an image being in a widget with a different aspect ratio. This makes the image to leave parts of the widget unoccupied.
Below is a codebase with Container having different dimensions hence different aspect ratios from the image itself.
// ...
class MyApp extends StatelessWidget {
  const MyApp({super.key});
  @override
  Widget build(BuildContext context) {
    return SafeArea(
        child: Scaffold(
            body: Container(
                decoration: BoxDecoration(
                  border: Border.all(color: Colors.red, width: 2.0),
                ),
                height: MediaQuery.of(context).size.height * 0.3,
                width: MediaQuery.of(context).size.width * 0.5,
                child: Image.asset("assets/images/sample.png"))));
  }
}
// ...
There's a parameter for Image.asset called fit where you can pass an enum value for BoxFit to specify how the image fills the Container.
BoxFit.fill distorts the image's aspect ratio so that it can fill the Container.
BoxFit.cover let's the image fill the Container without distorting the aspect ratio while cliping the sides of the image.
BoxFit.fitHeight and BoxFit.fitWidth depends on the aspect ratio of the image, that is, which side is more dorminant in size and hence should be used to fill the Container.
BoxFit.contain was the default. I may not say much for BoxFit.scaleDown so look into it.

I'll use BoxFit.cover because I'd recommend it more than the others.
// ...
child: Image.asset(
  "assets/images/sample.png",
  fit: BoxFit.cover
) // Image.asset