Welcome to the Treehouse Community

Want to collaborate on code errors? Have bugs you need feedback on? Looking for an extra set of eyes on your latest project? Get support with fellow developers, designers, and programmers of all backgrounds and skill levels here with the Treehouse Community! While you're at it, check out some resources Treehouse students have shared here.

Looking to learn something new?

Treehouse offers a seven day free trial for new students. Get access to thousands of hours of content and join thousands of Treehouse students and alumni in the community today.

Start your free trial

Android Build a Weather App Hooking Up the Model to the View Plugging in the Data

android:text="@{`At ` + String.valueOf(weather.formattedTime) + ` it will be`}"

Where did the .formattedTime come from ?

All I see is the getFormattedTime(); method...unless I'm missing something

2 Answers

Boban Talevski
Boban Talevski
24,793 Points

Calling weather.formattedTime actually accesses the getFormattedTime() method. That's just the way it works. https://developer.android.com/topic/libraries/data-binding/expressions

public class User {
  public final String firstName;
  public final String lastName;
  public User(String firstName, String lastName) {
      this.firstName = firstName;
      this.lastName = lastName;
  }
}
public class User {
  private final String firstName;
  private final String lastName;
  public User(String firstName, String lastName) {
      this.firstName = firstName;
      this.lastName = lastName;
  }
  public String getFirstName() {
      return this.firstName;
  }
  public String getLastName() {
      return this.lastName;
  }
}

From the perspective of data binding, these two classes are equivalent. The expression @{user.firstName} used for the android:text attribute accesses the firstName field in the former class and the getFirstName() method in the latter class. Alternatively, it is also resolved to firstName() if that method exists.

Stephen Wall
PLUS
Stephen Wall
Courses Plus Student 27,294 Points

In the course though, the getFormattedTime is a method that plays off of a member variable "time", which is represented as a long. The getFormattedTime method is therefore not accessible from the data binding and also caused errors for me going through the course. To get around this, I added a member variable "formattedTime" and in the CurrentWeather constructer added a line to populate it with the getFormattedTime method:

    private String formattedTime;

    public CurrentWeather() { }

    public CurrentWeather(String locationLabel, String icon, String timeZone, long time,
                          double temperature, double humidity, double precipChance, String summary) {
        this.locationLabel = locationLabel;
        this.icon = icon;
        this.timeZone = timeZone;
        this.time = time;
        this.temperature = temperature;
        this.humidity = humidity;
        this.precipChance = precipChance;
        this.summary = summary;
        this.formattedTime = getFormattedTime();  //<<< Right here was the fix for me. 
    }

    public String getFormattedTime() {
        SimpleDateFormat formatter = new SimpleDateFormat("h:mm a");
        formatter.setTimeZone(TimeZone.getTimeZone(timeZone));
        Date date = new Date(time * 1000);
        return formatter.format(date);
    }

Interestingly this still caused an issue with the layout showing my default value for the time while it was loading and would instead show "At null it will be ".... Maybe my version of Android Studio is the culprit.

I'm sure you're not here any more but the getFormattedTime method takes an argument. Without that, I'm surprised it compiles but the null would be caused by the returned string pointing to nothing.

I had the same issue with this error and implemented a similar solution to yours. It worked for me ... Github repo is here