Android: BaseAdapter и getLayoutInflater в отдельном файле класса

Прямо сейчас, чтобы заполнить свои GridViews, я использую расширенный класс BaseAdapter для каждого из моих действий Android (а их большинство).

Чтобы упростить чтение и поддержку, я пытаюсь поместить весь код BaseAdapter в отдельный файл класса.

Чтобы заполнить GridView, я использую LayoutInflater, и здесь все становится сложнее...

Поскольку getLayoutInflater() исходит из android.Activity, он просто не поможет. Я попытался сделать свой Adapter.java(класс для заполнения GridViews) расширенным классом Activity, а затем внутри создать класс BaseAdapter (так, как я делаю это прямо сейчас), но я не смог заставить его работать правильно.

Вот как выглядит Adapter.java:

//Adapter.java
package com.cimp.matitec;

import greendroid.app.GDActivity;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.TextView;

public class Adapter extends GDActivity{

public class ImageAdapter extends BaseAdapter
{
   Context MyContext;
   int count;
   String[] nombre;

   public ImageAdapter(Context _MyContext, int n, String[] nombre)
   {
      MyContext = _MyContext;
      count = n;
      this.nombre = nombre;
   }

   public int getCount()
   {
                     /* Set the number of element we want on the grid */
      return count;
   }

   @Override
   public View getView(int position, View convertView, ViewGroup parent)
   {
      View MyView = convertView;

      if ( convertView == null )
      {
         /*we define the view that will display on the grid*/

         //Inflate the layout
         LayoutInflater li = getLayoutInflater();
         MyView = li.inflate(R.layout.grid_item, null);

         // Add The Text!!!
         TextView tv = (TextView)MyView.findViewById(R.id.grid_item_text);
         tv.setText(nombre[position]+"");

         // Add The Image!!!           
         ImageView iv = (ImageView)MyView.findViewById(R.id.grid_item_image);
         iv.setImageResource(R.drawable.ic_launcher);
      }

      return MyView;
   }

   @Override
   public Object getItem(int arg0) {
      // TODO Auto-generated method stub
      return null;
   }

   @Override
   public long getItemId(int arg0) {
      // TODO Auto-generated method stub
      return 0;
   }
}
}

Чтобы вызвать его извне, я делаю следующее:

//MainClass.java
Adapter MyGridAdapter = new Adapter();
MyGrid = (GridView)findViewById(R.id.grid);
MyGrid.setAdapter(MyGridAdapter.new ImageAdapter(this, 6, nombreTema));

Приложение работает, но при попытке заполнить я получил исключение NullPointerException getLayoutInflater().

Кто-то знает, что мне не хватает, или как заставить его работать правильно?


person Hito_kun    schedule 28.12.2011    source источник
comment
Расширяет ли GDActivity Activity?   -  person Squonk    schedule 29.12.2011
comment
Да, это активность Greendroid   -  person Hito_kun    schedule 29.12.2011
comment
С точки зрения OO, адаптер не является действием, ваш код просто неразумен. Вы ищете простоту, но в конечном итоге со временем и сложностью, способ, рекомендованный Google, может быть не самым совершенным, но он самый разумный и эффективный, по крайней мере, IMO.   -  person yorkw    schedule 29.12.2011
comment
Я знаю, что это немного странно, но я не мог найти другого способа сделать это. Все, что мне нужно, это заставить BaseAdapter работать   -  person Hito_kun    schedule 29.12.2011


Ответы (4)


Существует больше способов получить объект LayoutInflater, чем непосредственно из объекта Activity. На самом деле, getLayoutInflater(), вероятно, просто удобный метод для этого:

LayoutInflater li = (LayoutInflater) myContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);

См. документацию для LayoutInflater.

person MH.    schedule 29.12.2011
comment
Я делал и пробовал что-то подобное при запуске, не знаю, почему тогда не работало, а теперь работает :). Большое спасибо. - person Hito_kun; 29.12.2011

вы должны передать контекст MainActivity при создании объекта класса, который расширяет baseadapter примерно так LayoutInflater inflater = ((Activity)MyContext)).getLayoutInflater;

это приведет MyContext к Activity, а затем можно будет вызвать GetLayoutInflater()!!

person shunryui nik    schedule 22.12.2014

Прочитайте это...

Основы работы с приложением

... особенно часть действий в разделе «Компоненты приложения».

НЕ пытайтесь создать экземпляр Activity с помощью new. Activity — это особый класс Android, и его НЕ следует рассматривать как обычный класс Java. Activity следует запускать только с помощью Intent, и ОС Android несет ответственность за его создание.

Другими словами, никогда не делайте этого...

Adapter MyGridAdapter = new Adapter();

Кроме того, Adapter — это имя класса виджетов Android, поэтому это не лучший выбор для имени одного из ваших собственных классов.

EDIT: Также см. мой ответ на этот вопрос здесь о создании вспомогательного класса и передаче ему Context активности.

person Squonk    schedule 28.12.2011
comment
Я уже делаю это, я отправляю контекст в BaseAdapter... Проблема в том, что я получаю The method getLayoutInflater() is undefined for the type ImageAdapter, поэтому я расширяюсь до Activity - person Hito_kun; 29.12.2011
comment
Вы, очевидно, не читали комментарий к моему ответу, где я объясняю другому человеку, как использовать mContext.getSystemService(...) в его случае. То же самое относится и к вашему MyContext (которое по соглашению должно начинаться со строчной буквы). Вы можете использовать MyContext.getLayoutInflater(), альтернативно getApplicationContext().getLayoutInflater() должно работать. В любом случае, никогда не пытайтесь создавать экземпляр Activity с new. - person Squonk; 29.12.2011
comment
Я прочитал то, что вы публикуете, и попробовал это... Я пытаюсь LayoutInflater li = MyContext.getLayoutInflater(); (позже я исправлю случаи, так как часть кода не принадлежит мне), и он показывает The method getLayoutInflater() is undefined for the type Context - person Hito_kun; 29.12.2011
comment
ОК, извините, его нужно преобразовать в Activity, как в ((Activity)MyContext).getLayoutInflater(). Я вижу, вы приняли ответ, и он работает, но это приведение от Context к Activity может пригодиться вам в будущих ситуациях. - person Squonk; 29.12.2011
comment
Да, это будет полезно. Большое спасибо. - person Hito_kun; 29.12.2011

Лучший способ — использовать объект статического метода LayoutInflator с контекстом приложения в качестве единственного параметра для получения инфлятора.

person babak    schedule 15.07.2017