1

In my view, I render a list of people with avatars. Here's my code in Github.

No problem with listing names, the problem is, when I output their avatar, that part of the view is "empty". It has a width, height, even a radius border but empty. Image URLs are Wikipedia URLs.

What should I check for? Thank you.

struct AvatarView: View {

    /// image
    let image: String

    var body: some View {

    Image(image)        // creates an imageview with specified image
        .resizable()    // makes image resizable
        .frame(width: 70, height: 70)
        .border(Color.gray.opacity(0.5), width: 0.5)
        .cornerRadius(35)
    }
}

This is how I call for Avatar view:

VStack() {

    HStack(spacing: 10) {

    // avatar
    AvatarView(image: scientist.image)

    VStack(alignment: .leading, spacing: 3) {
        Text(scientist.name).font(.headline)
5
  • you should give us a reproducable copyable example which shows the error/misbehaviour with real links to image. Commented Jan 24, 2020 at 13:47
  • I added my Github repo. Commented Jan 24, 2020 at 13:50
  • Image(image) means image should be local name in your bundle assets, not an URL. You need to load it manually from URL and only then create image from date, via UIImage. Commented Jan 24, 2020 at 14:27
  • @Asperi Thank you. I downloaded the image and tried to output like "images/einstein.jpg" or "./images/einstein.jpg". Result is the same. Also: What should I use to output an image from URL? Commented Jan 24, 2020 at 14:30
  • maybe look at this medium.com/@dmytro.anokhin/… Commented Jan 24, 2020 at 14:40

1 Answer 1

2

You have to load the images from the web, I replaced the image type with a UIImage instead of a String, downloaded the image and inititliased the Image with uiImage: image.

import SwiftUI

// Instructor struct to create our test model:
struct Scientist: Identifiable {

    /// unique id
    var id: String = UUID().uuidString

    /// user name
    let name: String

    /// user profile avatar
    var image: UIImage

    /// Init
    init(name: String, image: String) {
        self.name = name
        print("Download Started")

        let url = URL(string: image)
        let data = try? Data(contentsOf: url!) //make sure your image in this url does exist, otherwise unwrap in a if let check / try-catch
        self.image = UIImage(data: data!)!

    }

}

struct SciencesHistory {

    static func heros() -> [Scientist] {


        let scientist1 = Scientist(name: "Albert Einstein", image: "https://upload.wikimedia.org/wikipedia/commons/thumb/3/3e/Einstein_1921_by_F_Schmutzer_-_restoration.jpg/1920px-Einstein_1921_by_F_Schmutzer_-_restoration.jpg")
        let scientist2 = Scientist(name: "Niels Bohr", image: "https://upload.wikimedia.org/wikipedia/commons/thumb/6/6d/Niels_Bohr.jpg/440px-Niels_Bohr.jpg")
        let scientist3 = Scientist(name: "Max Planck", image: "https://upload.wikimedia.org/wikipedia/commons/thumb/c/c7/Max_Planck_1933.jpg/440px-Max_Planck_1933.jpg")

        return [scientist1, scientist2, scientist3]
    }


    func getData(from url: URL, completion: @escaping (Data?, URLResponse?, Error?) -> ()) {
        URLSession.shared.dataTask(with: url, completionHandler: completion).resume()
    }

}

struct AvatarView: View {

    /// image
    let image: UIImage

    /// body - default property for the view.
    var body: some View {

        Image(uiImage: image)        // creates an imageview with specified image
            .resizable()    // makes image resizable
            .frame(width: 70, height: 70)       // frame for the image (width, height)
             // creates border around the image with 0.5 thikness - this will create rounded view outside the image.
            .border(Color.gray.opacity(0.5), width: 0.5)
            .cornerRadius(35)  // This will hide the cutting portion outside the rounded view border - this is required as per the documentation.
    }
}

struct ScientistView: View{

    let scientist: Scientist

    /// body
    var body: some View {

        /// main vertical stack view - contains upper stackview and image
        VStack(spacing: 10) {

            // Upper Stackview - Contains Horizontal stack and post content
            VStack() {

                HStack(spacing: 10) {

                    // avatar
                    AvatarView(image: scientist.image)

                    VStack(alignment: .leading, spacing: 3) {
                        Text(scientist.name).font(.headline)
                        // Text(scientist.time).font(.subheadline)
                    }
                }

                // post content - specify nil for multi-line text
                Text(scientist.name)
            }
            .padding(.leading, 15)  // spacing from left edge of the view
            .padding(.trailing, 15) // spacing from right edge of the view

        }
        .padding(.top, 5)
    }

}

struct ContentView: View {

    let scienceHistory = SciencesHistory.heros()

    var body: some View {

        NavigationView {

                // List inside the navigationController
                List {

                    // loop through members of science history items:
                    ForEach(scienceHistory) { scientist in
                        ScientistView(scientist: scientist)
                    }
                }
                // Navbar title:
                .navigationBarTitle(Text("Science History"))
        }

    }
}

struct ContentView_Previews: PreviewProvider {
    static var previews: some View {
        ContentView()
    }
}

This is the output: Screenshot

Sign up to request clarification or add additional context in comments.

1 Comment

I'm new on Swift. I will check this on Monday. Thank you.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.