Как увеличить параллакс android - PullRequest
0 голосов
/ 05 мая 2020

Я пытаюсь реализовать увеличение параллакса, когда пользователь растягивает экран вниз, он должен увеличивать изображение заголовка, но это не работает. Может ли кто-нибудь помочь мне с правильным решением. Это изображение может продемонстрировать, что я хочу получить желаемый результат.

enter image description here

Это моя XML активности:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context="com.es.bws.views.activities.MealPlanDetailActivity">

    <com.google.android.material.appbar.AppBarLayout
        android:id="@+id/appbar"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:fitsSystemWindows="true"
        app:elevation="6dp"
        android:theme="@style/AppTheme.AppBarOverlay">

        <com.google.android.material.appbar.CollapsingToolbarLayout
            android:id="@+id/collapsing_toolbar"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            app:layout_scrollFlags="scroll|exitUntilCollapsed|snap"
            app:contentScrim="@android:color/transparent">

            <LinearLayout
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:background="@color/tab_background"
                android:orientation="vertical">

                <RelativeLayout
                    android:layout_width="match_parent"
                    android:layout_height="220dp">

                    <ImageView
                        app:layout_collapseMode="parallax"
                        android:id="@+id/mealIV"
                        android:layout_width="match_parent"
                        android:layout_height="match_parent"
                        android:scaleType="matrix" />

                    <LinearLayout
                        android:layout_width="wrap_content"
                        android:layout_height="wrap_content"
                        android:layout_alignParentEnd="true"
                        android:layout_alignParentBottom="true"
                        android:layout_margin="10dp">

                        <LinearLayout
                            android:id="@+id/changemeal_LL"
                            android:layout_width="100dp"
                            android:layout_height="35dp"
                            android:background="@drawable/rounded_edge"
                            android:gravity="center">

                            <TextView
                                android:layout_width="wrap_content"
                                android:layout_height="wrap_content"
                                android:text="@string/change_meal"
                                android:textColor="@color/black_app_color"
                                android:textSize="@dimen/medium_text_size" />

                        </LinearLayout>

                        <LinearLayout
                            android:id="@+id/logLL"
                            android:layout_width="100dp"
                            android:layout_height="35dp"
                            android:layout_marginLeft="5dp"
                            android:background="@drawable/rounded_edge"
                            android:gravity="center">

                            <ImageView
                                android:layout_width="20dp"
                                android:layout_height="30dp"
                                android:layout_gravity="center"
                                android:src="@mipmap/apple" />

                            <TextView
                                android:layout_width="wrap_content"
                                android:layout_height="wrap_content"
                                android:layout_marginLeft="5dp"
                                android:text="@string/log_meal"
                                android:textColor="@color/black_app_color"
                                android:textSize="@dimen/medium_text_size" />

                        </LinearLayout>
                    </LinearLayout>

                    <LinearLayout
                        android:id="@+id/backLL"
                        android:layout_width="50dp"
                        android:layout_height="40dp"
                        android:gravity="center_vertical">

                        <ImageView
                            android:id="@+id/backIV"
                            android:layout_width="25dp"
                            android:layout_height="25dp"
                            android:layout_marginLeft="10dp"
                            android:src="@mipmap/back_img" />
                    </LinearLayout>

                    <ProgressBar
                        android:id="@+id/pb"
                        android:layout_width="wrap_content"
                        android:layout_height="wrap_content"
                        android:layout_centerInParent="true" />

                </RelativeLayout>

            </LinearLayout>

            <androidx.appcompat.widget.Toolbar
                android:id="@+id/toolbar"
                android:layout_width="match_parent"
                android:layout_height="100dp"
                android:visibility="gone"
                app:layout_collapseMode="pin">

            </androidx.appcompat.widget.Toolbar>

        </com.google.android.material.appbar.CollapsingToolbarLayout>

    </com.google.android.material.appbar.AppBarLayout>

    <androidx.core.widget.NestedScrollView
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        app:layout_behavior="@string/appbar_scrolling_view_behavior">

        <include layout="@layout/meal_content_layout" />

    </androidx.core.widget.NestedScrollView>

    <LinearLayout
        android:visibility="gone"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical"
        app:layout_behavior="@string/appbar_scrolling_view_behavior">


        <View
            android:layout_width="match_parent"
            android:layout_height="10dp" />

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:background="@color/tab_background">

            <RadioGroup
                android:id="@+id/activity_onsite"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:layout_centerHorizontal="true"
                android:layout_centerVertical="true"
                android:divider="?android:attr/dividerHorizontal"
                android:orientation="horizontal"
                android:showDividers="middle">

                <RadioButton
                    android:id="@+id/ingradient_radio"
                    android:layout_width="0dp"
                    android:layout_height="wrap_content"
                    android:layout_weight="0.5"
                    android:button="@null"
                    android:checked="true"
                    android:gravity="center"
                    android:padding="10dp"
                    android:text="@string/ingredients"
                    android:textColor="@color/black_app_color" />
                <!--<view-->
                <!--android:layout_width="1dp"-->
                <!--android:layout_height="match_parent"-->
                <!--android:layout_marginTop="5dp"-->
                <!--android:layout_marginBottom="5dp"-->
                <!--android:background="@color/tab_divider"/>-->
                <RadioButton
                    android:id="@+id/preparation_radio"
                    android:layout_width="0dp"
                    android:layout_height="wrap_content"
                    android:layout_weight="0.5"
                    android:button="@null"
                    android:gravity="center"
                    android:padding="10dp"
                    android:text="@string/preparation"
                    android:textColor="@color/black_app_color" />
            </RadioGroup>

        </LinearLayout>

        <LinearLayout
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:orientation="horizontal"
            android:weightSum="1">

            <View
                android:id="@+id/ingradient_underline"
                android:layout_width="match_parent"
                android:layout_height="2dp"
                android:layout_weight="0.5"
                android:background="@color/yellow" />

            <View
                android:id="@+id/preparation_underline"
                android:layout_width="match_parent"
                android:layout_height="2dp"
                android:layout_weight="0.5"
                android:background="@color/yellow"
                android:visibility="invisible" />
        </LinearLayout>

        <androidx.recyclerview.widget.RecyclerView
            android:id="@+id/ingradientParentRV"
            android:layout_width="match_parent"
            android:layout_height="wrap_content" />

        <androidx.core.widget.NestedScrollView
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:scrollbars="none">

            <TextView
                android:id="@+id/preparationTV"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:layout_below="@+id/tab_line"
                android:padding="10dp"
                android:textSize="@dimen/medium_text_size"
                android:visibility="gone" />
        </androidx.core.widget.NestedScrollView>
    </LinearLayout>
</LinearLayout>



Это мой код активности:

public class MealPlanDetailActivity extends BaseActivity implements View.OnClickListener, AppBarLayout.OnOffsetChangedListener {
    RadioButton inch_radio;
    RadioButton cm_radio;
    View inch_underline;
    View cm_underline;
    ImageView mealIV;
    LinearLayout backLL;
    LinearLayout logLL;
    TextView mealNameTV;
    TextView mealDetailTV;
    TextView mealTimeTV;
    TextView calTV;
    TextView protTV;
    TextView fatTV;
    TextView cabTV;
    TextView ingradientTV;
    TextView preparationTV;
    TextView preperationRecipeTVV;
    TextView unsaturatedFatTV;
    TextView saturatedFatTV;
    TextView fiberTV;

    RecyclerView ingradientRV;
    RecyclerView ingradientParentRV;
    Button selectMealBtn;
    private LinearLayoutManager linearLayoutManager;
    private LinearLayoutManager parentLinearLayoutManager;
    ProgressBar pb;
    Dialog dialog;
    ImageView mealIVV;
    ProgressBar pbb;
    TextView recipeNameTV;
    TextView timeTV;
    LinearLayout changemeal_LL;

    MealsDaysCommonStruct mealsDaysStruct;
    PastryAndDrinkStruct pastryStruct;
    FoodByDayDetailStruct struct;
    MealsDaysCommonStruct recipeStruct;

    TextView inGradientRecipeTV;
    TextView preperationRecipeTV;
    View inGradientRecipeV;
    View preparatiomRecipeV;
    ImageView selectedRecipeCloseIV;

    int delayTime = 3000;

    private float collapsedScale;
    private float expandedScale;

    Toolbar toolbar;
    AppBarLayout mAppBarLayout;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_meal_explaination);
        if (singleton.isUserAvailable()) {
            mealsDaysStruct = (MealsDaysCommonStruct) getIntent().getSerializableExtra("SELECTED_MEAL");
            pastryStruct = (PastryAndDrinkStruct) getIntent().getSerializableExtra("MEAL_CAKE_DRINK");
            init();
            setListener();
            if (mealsDaysStruct != null)
                makeGetMealDetailCall(true, mealsDaysStruct.getId());
            else {
                logLL.setVisibility(View.VISIBLE);
                changemeal_LL.setVisibility(View.GONE);

                makeGetMealDetailCall(true, pastryStruct.getId());
            }
        }
    }

    private void setData() {
        if (singleton.isFav == 1) {
            changemeal_LL.setVisibility(View.GONE);
        }
        mealNameTV.setText(struct.getName());
        mealTimeTV.setText(struct.getMinutesForPreparation() + " min");
        calTV.setText(struct.getCalories());
        cabTV.setText(struct.getCarbs());
        fatTV.setText(struct.getTotalFat());
        protTV.setText(struct.getProteins());
        unsaturatedFatTV.setText(struct.getUnsaturatedFats());
        saturatedFatTV.setText(struct.getSaturatedFats());
        fiberTV.setText(struct.getFiber());
        singleton.loadImage(struct.getImageUrl(), mealIV, pb, false);
        preparationTV.setText(Html.fromHtml(struct.getPreparation()));
        ingradientParentRV.setAdapter(new IngradientAdapter(mAct, singleton.ingredientList));
    }

    private void init() {
        struct = new FoodByDayDetailStruct();
        inch_radio = findViewById(R.id.ingradient_radio);
        cm_radio = findViewById(R.id.preparation_radio);
        inch_underline = findViewById(R.id.ingradient_underline);
        cm_underline = findViewById(R.id.preparation_underline);
        calTV = findViewById(R.id.calTV);
        protTV = findViewById(R.id.protTV);
        fatTV = findViewById(R.id.fatTV);
        cabTV = findViewById(R.id.cabTV);
        backLL = findViewById(R.id.backLL);
        preparationTV = findViewById(R.id.preparationTV);
        pb = findViewById(R.id.pb);
        mealNameTV = findViewById(R.id.mealNameTV);
        mealDetailTV = findViewById(R.id.mealDetailTV);
        mealTimeTV = findViewById(R.id.mealTimeTV);
        mealIV = findViewById(R.id.mealIV);
        logLL = findViewById(R.id.logLL);
        unsaturatedFatTV = findViewById(R.id.unsaturatedFatTV);
        saturatedFatTV = findViewById(R.id.saturatedFatTV);
        fiberTV = findViewById(R.id.fiberTV);
        changemeal_LL = findViewById(R.id.changemeal_LL);
        ingradientParentRV = findViewById(R.id.ingradientParentRV);

        parentLinearLayoutManager = new LinearLayoutManager(this);
        ingradientParentRV.setLayoutManager(parentLinearLayoutManager);

        toolbar = (Toolbar) findViewById(R.id.toolbar);
        setSupportActionBar(toolbar);

        getSupportActionBar().setDisplayHomeAsUpEnabled(true);

        mAppBarLayout = (AppBarLayout) findViewById(R.id.appbar);
        mAppBarLayout.addOnOffsetChangedListener(this);
    }

    private void setListener() {
        inch_radio.setOnClickListener(this);
        cm_radio.setOnClickListener(this);
        changemeal_LL.setOnClickListener(this);
        logLL.setOnClickListener(this);
        backLL.setOnClickListener(this);
        mealIV.setOnClickListener(this);
    }

    public void setTabsPager(MealsDaysCommonStruct struct) {
        this.mealsDaysStruct = struct;
        makeGetMealDetailCall(false, mealsDaysStruct.getId());
    }

    @Override
    public void onBackPressed() {
//        singleton.commonStatus = singleton.Meal;
        singleton.finishActivity();
    }

    @Override
    public void onClick(View v) {
        switch (v.getId()) {
            case R.id.ingradient_radio: {
                inch_underline.setVisibility(View.VISIBLE);
                cm_underline.setVisibility(View.INVISIBLE);
                ingradientParentRV.setVisibility(View.VISIBLE);
                preparationTV.setVisibility(View.GONE);
                break;
            }
            case R.id.preparation_radio: {
                preparationTV.setText(struct.getPreparation());
                inch_underline.setVisibility(View.INVISIBLE);
                cm_underline.setVisibility(View.VISIBLE);
                ingradientParentRV.setVisibility(View.GONE);
                preparationTV.setVisibility(View.VISIBLE);
                break;
            }
            case R.id.backLL: {
//                singleton.commonStatus = singleton.Meal;
                onBackPressed();
                break;
            }
            case R.id.changemeal_LL: {
                if (singleton.loginStruct.getSubscriptionsList() != null && singleton.loginStruct.getSubscriptionsList().size() > 0) {
                    makeChangeMealCall();
                } else {
//                    singleton.commonStatus = singleton.MEAL_DETAIL;
                    singleton.startActivity(SubscriptionsActivity.class, singleton.START_ACTIVITY);
                }

                break;
            }
            case R.id.logLL: {
                makeLogMealCall();
                break;
            }
            case R.id.inGradientRecipeTV: {
                preperationRecipeTVV.setVisibility(View.GONE);
                ingradientRV.setVisibility(View.VISIBLE);
                inGradientRecipeV.setVisibility(View.VISIBLE);
                preparatiomRecipeV.setVisibility(View.INVISIBLE);
                break;
            }
            case R.id.preperationRecipeTV: {
                preperationRecipeTVV.setVisibility(View.VISIBLE);
                ingradientRV.setVisibility(View.GONE);
                inGradientRecipeV.setVisibility(View.INVISIBLE);
                preparatiomRecipeV.setVisibility(View.VISIBLE);
                break;
            }
            case R.id.selectedRecipeCloseIV: {
                dialog.dismiss();
                break;
            }
            case R.id.selectMealBtn: {
//                makeGetMealDetailCall(true,mealsDaysStruct.getId());
                setData();
                singleton.upDateMeal(struct);
                singleton.isMealChange = true;
                dialog.dismiss();
                break;
            }
            case R.id.mealIV:{
                Bundle bundle = new Bundle();
                bundle.putString("ImageUrl" , struct.getImageUrl());
                singleton.startActivityWithDataBundle(MealImageViewActivity.class , bundle , singleton.START_ACTIVITY);
                break;
            }
        }
    }

    private void makeGetMealDetailCall(Boolean key, int mealId) {
        singleton.showProgress(getString(R.string.please_wait));
        Map<String, Object> params = new HashMap<>();
        params.put("meal_id", mealId);
        Call<Object> call = singleton.getApiInterface().postCall("Bearer " + singleton.TOKEN, "get-meal-detail", params);
        OnServerResCallBack callBack = (status, message, responseStr) -> {
            if (status == singleton.SUCCESS) {
                JSONObject obj = singleton.parseSuccessPartOfJSON_OBJ(responseStr, "detail");
                struct = gson.fromJson(obj.toString(), FoodByDayDetailStruct.class);
                singleton.ingredientList = struct.getIngredients();
                if (key == true) {
                    setData();
                } else {
                    dialog();
                    setMealDetailDialog();
                }
            } else {
                singleton.showCommonDialog(null, getString(R.string.error), message, getString(R.string.ok), false);
            }
            singleton.dismissProgress();
        };
        singleton.makePostCall(call, callBack);
    }

    private void makeLogMealCall() {
        singleton.showProgress(getString(R.string.please_wait));
        Map<String, Object> params = new HashMap<>();

        params.put("meal_id", struct.getId());
        params.put("meal_time_id", singleton.getMealTypeId(singleton, singleton.mealType));
        if (singleton.isFav == 0) {
            params.put("food_plan_id", singleton.loginStruct.getFoodStartedStruct().getFoodPlanId());
        }
        Call<Object> call = singleton.getApiInterface().postCall("Bearer " + singleton.TOKEN, "log-meal", params);
        OnServerResCallBack callBack = (status, message, responseStr) -> {
            if (status == singleton.SUCCESS) {
                JSONObject obj = singleton.parseSuccessPartOfJSON_OBJ(responseStr, "award");
                if (obj.has("message")) {
                    singleton.isLogMealAward = true;
                } else {
                    OnDialogCallBack dialogCallBack = isOkClick -> singleton.finishActivity();
                    singleton.showDialog(dialogCallBack , getString(R.string.great) , getString(R.string.you_logged_your_meal) , "Ok" );
                }

            } else {
                singleton.showCommonDialog(null, getString(R.string.error), message, getString(R.string.ok), false);
            }
            singleton.dismissProgress();
        };
        singleton.makePostCall(call, callBack);
    }

    public void showDialogChangeMealSelection(FoodByDayDetailStruct detailStruct) {
        struct = detailStruct;
        makeGetMealDetailCall(false, struct.getId());
    }

    public void dialog() {
        dialog = new Dialog(this);
        dialog.requestWindowFeature(Window.FEATURE_NO_TITLE);
        dialog.setCancelable(false);
        dialog.setContentView(R.layout.dialog_change_meal_selection);
        dialog.getWindow().setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT));
        initDialog();
        setListenerDialod();
        dialog.show();
    }

    private void setListenerDialod() {
        inGradientRecipeTV.setOnClickListener(this);
        preperationRecipeTV.setOnClickListener(this);
        selectedRecipeCloseIV.setOnClickListener(this);
        selectMealBtn.setOnClickListener(this);
    }

    private void initDialog() {
        mealIVV = dialog.findViewById(R.id.mealIVV);
        pbb = dialog.findViewById(R.id.pbb);
        recipeNameTV = dialog.findViewById(R.id.recipeNameTV);
        timeTV = dialog.findViewById(R.id.timeTV);

        preperationRecipeTV = dialog.findViewById(R.id.preperationRecipeTV);
        inGradientRecipeV = dialog.findViewById(R.id.inGradientRecipeV);
        preparatiomRecipeV = dialog.findViewById(R.id.preparatiomRecipeV);
        inGradientRecipeTV = dialog.findViewById(R.id.inGradientRecipeTV);
        selectedRecipeCloseIV = dialog.findViewById(R.id.selectedRecipeCloseIV);
        preperationRecipeTVV = dialog.findViewById(R.id.preperationRecipeTVV);
        ingradientRV = dialog.findViewById(R.id.ingradientRV);
        selectMealBtn = dialog.findViewById(R.id.selectMealBtn);
    }

    private void makeChangeMealCall() {
        singleton.showProgress(getString(R.string.please_wait));
        Map<String, Object> params = new HashMap<>();
        params.put("food_plan_id", singleton.loginStruct.getFoodStartedStruct().getFoodPlanId());
        params.put("meal_time_id", singleton.getMealTypeId(singleton, singleton.mealType));
        Call<Object> call = singleton.getApiInterface().postCall("Bearer " + singleton.TOKEN, "get-meals-for-change", params);
        OnServerResCallBack callBack = (status, message, responseStr) -> {
            if (status == singleton.SUCCESS) {
                JSONArray jsonArray = singleton.parseSuccessPartOfJSON(responseStr, "meals");
                List<FoodByDayDetailStruct> list = gson.fromJson(jsonArray.toString(), new TypeToken<ArrayList<FoodByDayDetailStruct>>() {
                }.getType());
                Collections.shuffle(list);

                singleton.showDialogChangeMeal(mAct, struct.getId(), list);
            } else {
                singleton.showCommonDialog(null, getString(R.string.error), message, getString(R.string.ok), false);
            }
            singleton.dismissProgress();
        };
        singleton.makePostCall(call, callBack);
    }

    private void setMealDetailDialog() {
        linearLayoutManager = new LinearLayoutManager(this);
        ingradientRV.setLayoutManager(linearLayoutManager);

        recipeNameTV.setText(struct.getName());
        timeTV.setText(struct.getMinutesForPreparation().toString() + " min");
        preperationRecipeTVV.setText(Html.fromHtml(struct.getPreparation()));
        singleton.loadImage(struct.getImageUrl(), mealIVV, pbb, false);
        ingradientRV.setAdapter(new IngradientAdapter(mAct, singleton.ingredientList));
    }

    @Override
    public void onOffsetChanged(AppBarLayout appBarLayout, int i) {
        int maxScroll = appBarLayout.getTotalScrollRange();

        float scrollPercent = (float) Math.abs(i) / (float) maxScroll;

        if (collapsedScale == 0) {

            Drawable photo = mealIV.getDrawable();

            int bitmapWidth = photo.getIntrinsicWidth();
            int bitmapHeight = photo.getIntrinsicHeight();

            collapsedScale = (float)mealIV.getWidth()/(float)bitmapWidth;
            expandedScale = (float)mealIV.getHeight()/(float)bitmapHeight;

            scalePhotoImage(mealIV, expandedScale);

        } else {
            scalePhotoImage(mealIV, collapsedScale + (expandedScale - collapsedScale) * (1f - scrollPercent));
        }
    }

    private static void scalePhotoImage(ImageView photoView, float scale) {

        Drawable photo = photoView.getDrawable();

        int bitmapWidth = photo.getIntrinsicWidth();
        int bitmapHeight = photo.getIntrinsicHeight();

        float offsetX = (photoView.getWidth() - bitmapWidth) / 2F;
        float offsetY = (photoView.getHeight() - bitmapHeight) / 2F;

        float centerX = photoView.getWidth() / 2F;
        float centerY = photoView.getHeight() / 2F;

        Matrix imageMatrix = new Matrix();
        imageMatrix.setScale(scale, scale, centerX, centerY);
        imageMatrix.preTranslate(offsetX, offsetY);

        photoView.setImageMatrix(imageMatrix);
    }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...