이번엔 GridLayout을 위한 adapter를 만들어보도록 하겠습니다. 그렇게 큰 차이는 없으나 이번엔 Retrofit를 이용한 통신까지 적용하겠습니다.


1. ViewHolder 지정


public class FlowerAdapter_grid extends RecyclerView.Adapter<FlowerAdapter_grid.Holder> {
 
    private static final Object TAG = FlowerAdapter_grid.class.getSimpleName();
    private final FlowerClickListener mListener;
    private List<Flower> mFlowers;
    public FlowerAdapter_grid(FlowerClickListener listener) {
        mFlowers = new ArrayList<>();
        mListener = listener;
    }
}
cs

GridLayout도 일종의 RecyclerView입니다. 그러므로 RecyclerView에서 GridLayout을 위한 뷰홀더를 작성할 것입니다. 그러기 위해선 ViewHolder의 extends가 필요합니다. 변수지정은 따로 언급하지 않겠습니다.


    @Override
    public Holder onCreateViewHolder(ViewGroup parent, int viewType) {
        View row = LayoutInflater.from(parent.getContext()).inflate(R.layout.row_item_grid, parent, false);
        return new Holder(row);
    }
cs

ViewHolder가 작성될 때 바로 layout에 적용될 수 있게 LayoutInflater.from(parent.getContext()).inflate(R.layout.row_item_grid, parent, false) 이 부분이 필요합니다. 그리고 지난시간에도 그랬듯이 ViewHolder처리 과정에서 Glide도 처리해줍니다. 

    @Override
    public void onBindViewHolder(Holder holder, int position) {
        Flower currFlower = mFlowers.get(position);
        Glide.with(holder.itemView.getContext())
                .load(currFlower.getImage())
                .thumbnail(0.5f)
                .crossFade()
                .into(holder.mImage);
    }
cs


이번엔 Glide를 thumbnail로 쓸 것입니다. 0.5f는 원본의 0.5만큼의 수준으로 thumbnail로 사용한다는 뜻입니다. crossfade()를 통해 애니메이션 효과도 부여할 수 있습니다.


    @Override
    public int getItemCount() {
        return mFlowers.size();
    }
 
    public void addFlower(Flower flower) {
        mFlowers.add(flower);
        notifyDataSetChanged();
    }
cs


이렇게 포스트의 사이즈를 가져오거나 새로운 포스트를 추가할 수 있습니다. 지난번과 코드가 동일합니다.


    public void clear(){
        mFlowers.clear();
        notifyDataSetChanged();
    }
 
    public Flower getSelectedFlower(int position) {
        return mFlowers.get(position);
    }
cs


포스트를 클리어할 때 사용됩니다. 지난번과 같은 코드입니다.


public class MyPagerAdapter extends FragmentPagerAdapter {
 
    public Fragment[] arrFragments;
    public MyPagerAdapter(FragmentManager fm, Fragment[] arrFragmnets) {
        super(fm);
        this.arrFragments = arrFragmnets;
    }
 
    @Override
    public Fragment getItem(int position) {
        return arrFragments[position];
    }
 
    @Override
    public int getCount() {
        return arrFragments.length;
    }
}
cs


이렇게 Fragment에 Adapter를 달아줍니다. 이제 여기선 apiservice도 작성할 것입니다. 위에선 Fragment getItem() 에서 arrFragments의 position 값을 return 합니다. 포스트의 수를 세기 위해 getCount()를 작성했습니다. arrFragments.length가 전체 포스트의 수를 반영합니다.


2. apiService 작성


public interface FlowerApiService {
 
    @GET("posts/")
    Call<List<Flower>> getAllFlowers(@Query("user_lat"String lat, @Query("user_lon"String lon);
}
cs


다른 apiservice 도 만들도록 합니다. apiService는 사전에 만들어둠으로써 나중에 retrofit 통신을 수월하게 해 줍니다. 포스트들의 위도와 경도값을 받는 apiservice를 만들겠습니다.


public interface LoginApiService {
 
    String string = "client_Id";
 
    @POST("rest-auth/login/")
    Call<MyKey> getget(@Body LoginData loginData);
}
cs

이것은 로그인을 위한 apiService입니다. 로그인시에 필요한 데이터를 받습니다. 어디로 데이터를 전송할지 url을 설정할 수 있습니다. 저는 @POST("rest-auth/login/")에서 나와있듯 host주소/rest-auth/login/으로 통신할 것입니다. 


public interface PostApiService {
 
    @Multipart
    @POST("posts/")
    Call<ResponseBody> uploadFile (@Part MultipartBody.Part part, @Part("point") RequestBody pointString, @Part("text") RequestBody textString);
}
cs


이 것은 포스트를 위한 apiService입니다. 이 것을 통해 글의 등록이 가능합니다. 주소가 바뀌었습니다. 위의 주소와 다른 주소로 통신합니다.

그 다음은 유저 등록을 위한 부분입니다. 유저 등록을 위한 주소가 따로 존재합니다.


public interface RegistrationApiService {
    @Multipart
    @POST("rest-auth/registration/")
    Call<ResponseBody> registersecond (@Part("username") RequestBody username, @Part("email") RequestBody email, @Part("password1") RequestBody password1, @Part("password2") RequestBody password2);
}
cs


유저 등록시에 비밀번호와 비밀번호 재확인을 위해 두 번 변수를 입력받기 때문에 @Part 부분이 여러개로 나눠져있습니다. 


3. REST Manager 작성

저는 서버와 클라이언트의 REST통신을 이용하고 있으므로 REST 통신을 위한 apiservice도 만들어주면 편리합니다.

서버에서 http요청의 header값을 살펴보게 되므로 그 header값을 자동으로 지정해주는 RestManager를 작성하겠습니다.



public class RestManager {
 
    static Context mContext;
 
    private FlowerApiService mFlowerApiService;
 
    public FlowerApiService getmFlowerApiService(Context context) {
        if (mFlowerApiService==null) {
 
            mContext = context;
 
            OkHttpClient client = new OkHttpClient();
            OkHttpClient.Builder builder = new OkHttpClient.Builder();
            builder.interceptors().add(new AddCookiesInterceptor(mContext));
            client = builder.build();
 
            Retrofit retrofit = new Retrofit.Builder()
                    .client(client)
                    .baseUrl(Constants.BASE_URL)
                    .addConverterFactory(GsonConverterFactory.create())
                    .build();
 
            mFlowerApiService = retrofit.create(FlowerApiService.class);
        }
 
        return mFlowerApiService;
    }
}
cs

이러면 자동으로 okhttpclient에 헤더와 바디를 추가해줍니다. 원하는 대로 원하는 값을 넣을 수 있으므로 필요하신 대로 작성하셔서 쓰면 됩니다. GsonConverterFactory는 구글에서 제공하는 json데이터 처리용 도구입니다. retrofit를 이용해서 통신을 할 때마다 쉽게 헤더를 조절할 수 있기에 여러가지 만들어두고 사용하시면 편리할 것입니다.


+ Recent posts