Ładowanie zasobów: bezradność, złość, halucynacje

Ładowanie zasobów: bezradność, złość, halucynacje
calineczka
  • Rejestracja: dni
  • Ostatnio: dni
  • Postów: 33
2

Stworzyłam sobie projekt JavaFX z Mavenem i mam problem z załadowaniem obrazka (i zasobów ogólnie). Oto struktura plików jaką sobie utowrzyłam:

screenshot-20220309195355.png

A to sposób w jaki odwołuję się do zasobu:

Kopiuj
Image myImage = new Image(Objects.requireNonNull(getClass().getResourceAsStream("/img/domek.jpg")));

A w rezultacie dostaję null - kompletnie nie rozumiem dlaczego! Przecież główną scenę ładuję w podobny sposób i nie ma takich problemów:

Kopiuj
FXMLLoader fxmlLoader = new FXMLLoader(this.getClass().getResource("/fxml/application.fxml"));

W czym rzecz?

S9
  • Rejestracja: dni
  • Ostatnio: dni
  • Lokalizacja: Warszawa
  • Postów: 1092
2

@calineczka: ja w moim WinampEE korzystam z Guavy i mam:

Kopiuj
  private static final Image EMPTY_CD_IMAGE = new Image(getResource("images/empty_cd.jpg").toString());

images to katalog w resourcas (czyli resources/images/empty_cd.jpg)
U mnie działa, getResource pochodzi z tej klasy

calineczka
  • Rejestracja: dni
  • Ostatnio: dni
  • Postów: 33
0

@scibi_92: Nope, jak ładuję w taki sposób, też dostaję nullptr.

S9
  • Rejestracja: dni
  • Ostatnio: dni
  • Lokalizacja: Warszawa
  • Postów: 1092
0

@calineczka: czyli Guavą próbowałaś? Bez "/" na początku Stringa, dostajesz null string? Coś mi tu nie pasuje, Guava mówi że jak nie ma zasobu to powinna rzucić IllegalArgumentException

calineczka
  • Rejestracja: dni
  • Ostatnio: dni
  • Postów: 33
0

@scibi_92: Próbowałam tego: new Image(getResource("/img/domek.jpg").toString()); i tego new Image(getResource("img/domek.jpg").toString());
Bez '/' na początku nie mam żadnych szans na wczytanie czegokolwiek, przerabiałam to przez 2 godziny wczoraj. Nie mam pojęcia co to jest WimampEE (Winamp?) i Guava (jakaś biblioteka od google?) - chcę to zrobić na czystej JavieFX i Mavenie. Jeżeli się tego nie da zrobić bez zewnętrznych bibliotek, to oznacza że JavaFX jest skrajnie upośledzona i nieużywalna (co zaskakujące, bo korzystałam z AvaloniaUI i myślałam, ze gorzej już nie będzie...). ;/

Wibowit
  • Rejestracja: dni
  • Ostatnio: dni
  • Lokalizacja: XML Hills
0

ta metoda z guavy odwołuje się bezpośrednio do classloaderów

Kopiuj
/**
 * Returns a {@code URL} pointing to {@code resourceName} if the resource is found using the
 * {@linkplain Thread#getContextClassLoader() context class loader}. In simple environments, the
 * context class loader will find resources from the class path. In environments where different
 * threads can have different class loaders, for example app servers, the context class loader
 * will typically have been set to an appropriate loader for the current thread.
 *
 * <p>In the unusual case where the context class loader is null, the class loader that loaded
 * this class ({@code Resources}) will be used instead.
 *
 * @throws IllegalArgumentException if the resource is not found
 */
@CanIgnoreReturnValue // being used to check if a resource exists
// TODO(cgdecker): maybe add a better way to check if a resource exists
// e.g. Optional<URL> tryGetResource or boolean resourceExists
public static URL getResource(String resourceName) {
  ClassLoader loader =
      MoreObjects.firstNonNull(
          Thread.currentThread().getContextClassLoader(), Resources.class.getClassLoader());
  URL url = loader.getResource(resourceName);
  checkArgument(url != null, "resource %s not found.", resourceName);
  return url;
}
YA
  • Rejestracja: dni
  • Ostatnio: dni
  • Postów: 2384
1

Pomiń wiodący / i dodaj katalog resources do classpatha. Dalej null?

S9
  • Rejestracja: dni
  • Ostatnio: dni
  • Lokalizacja: Warszawa
  • Postów: 1092
0

@calineczka:

Jeżeli się tego nie da zrobić bez zewnętrznych bibliotek, to oznacza że JavaFX jest skrajnie upośledzona i nieużywalna

wczytywanie zasobów z resourców to nie jest domena JavaFX.
Anyway, bez Guavy u mnie tez działa:

Kopiuj
private static final Image EMPTY_CD_IMAGE = new Image(AlbumCoverController.class.getResource("/images/empty_cd.jpg").toString());

Z jakiego IDE korzystasz?

MrMadMatt
  • Rejestracja: dni
  • Ostatnio: dni
  • Postów: 373
0

Znając życie problem leży w tym że fxml leży w katalogu /resouces/settings.fxml a this.getClass() ma ścieżkę zasobów w jakimś com/company/myapp bo pobierając getClass() odnosisz się do katalogu zasobów klasy a nie głównego katalogu resources.

IMHO Jak ma się kontroler w com.company.app to fxml powinno się trzymać w jakimś resources/com/company/app

GS
  • Rejestracja: dni
  • Ostatnio: dni
  • Postów: 1265
0

https://mkyong.com/java/java-read-a-file-from-resources-folder/

W skrócie, może trzeba użyć classLoadera, tak jak w guavie, u Wibowita:

Kopiuj
ClassLoader classLoader = getClass().getClassLoader();
InputStream inputStream = classLoader.getResourceAsStream("/img/domek.jpg"));

Osobiście nie sprawdzałem.

RA
  • Rejestracja: dni
  • Ostatnio: dni
  • Postów: 54
1

Masz w ogóle te pliki w katalogu target/?

calineczka
  • Rejestracja: dni
  • Ostatnio: dni
  • Postów: 33
0

@scibi_92: Ah klasyka informatyków wszelkiej maści, "U mnie działa" :| IDE to IntelliJ IDEA 2021.3.3

@yarel: HA! Działa (wstępnie), ale jak usunę wiodącego / to się wysypuje - tak jak wspominałam, wczoraj straciłam 2 godziny na szukaniu dlaczego ta durnota nie chce mi załadować fxmla :|
W każdym razie, dziękuję ślicznie!

EDIT: Pytanie dlaczego - skoro ponoć katalogu resources/ nie było w classpath - udawało mi się wgrywać FXMLe znajdujące się w resources/fxml/...? 0_o

YA
  • Rejestracja: dni
  • Ostatnio: dni
  • Postów: 2384
0

EDIT: Pytanie dlaczego - skoro ponoć katalogu resources/ nie było w classpath - udawało mi się wgrywać FXMLe znajdujące się w resources/fxml/...? 0_o

A ktoż to może wiedzieć. Zawsze możesz uruchomić debugger i zobaczyć jak wygląda wyszukiwanie resource i który classloader za to odpowiada.

Skąd wiadomo, że się udawało? Może FXMLLoader dostał nulla i go przęłknął? I jak się udawało, w IDE czy uruchamiając via maven?

Zarejestruj się i dołącz do największej społeczności programistów w Polsce.

Otrzymaj wsparcie, dziel się wiedzą i rozwijaj swoje umiejętności z najlepszymi.