Выбранный элемент меняется при прокрутке

У меня есть дочерний макет и родительский макет, как показано ниже. Мне нужно выбрать несколько элементов в дочернем макете. Я могу выбрать несколько элементов, но столкнулся с двумя проблемами. 1. При прокрутке выбранный элемент меняется. 2. Когда я выбираю элемент в первой строке, также выбирается строка элемента 4.

Вот мой код.

Родительский макет:

    <?xml version = "1.0" encoding = "utf-8"?>
<RelativeLayout xmlns:android = "http://schemas.android.com/apk/res/android"
    android:layout_width = "match_parent"
    android:layout_height = "match_parent">
    <RelativeLayout
        android:layout_width = "match_parent"
        android:layout_height = "wrap_content"
        android:layout_alignParentTop = "true"
        android:id = "@+id/formsheader">
        <include
            android:id = "@+id/formToolbar"
            layout = "@layout/toolbar" />
    </RelativeLayout>
    <RelativeLayout
        android:layout_width = "match_parent"
        android:layout_height = "match_parent"
        android:orientation = "vertical"
        android:background = "#e9e7e9"
        android:layout_above = "@+id/formsfooter"
        android:layout_below = "@+id/formsheader"
        android:id = "@+id/teamFormsContent">
        <GridView
            android:layout_width = "match_parent"
            android:layout_height = "match_parent"
            android:columnWidth = "137dp"
            android:numColumns = "auto_fit"
            android:verticalSpacing = "20dp"
            android:horizontalSpacing = "20dp"
            android:stretchMode = "columnWidth"
            android:layout_marginLeft = "23dp"
            android:layout_marginRight = "23dp"
            android:layout_centerHorizontal = "true"
            android:layout_centerVertical = "true"
            android:scrollbars = "none"
            android:id = "@+id/form_gridView" />
    </RelativeLayout>
    <RelativeLayout
        android:layout_width = "match_parent"
        android:layout_height = "50dp"
        android:layout_alignParentBottom = "true"
        android:id = "@+id/formsfooter"
        android:layout_gravity = "center"
        android:gravity = "center"
        android:layout_centerHorizontal = "true"
        android:layout_centerVertical = "true"
        android:background = "#051b2e">
        <TextView
            android:id = "@+id/idletext"
            android:layout_width = "wrap_content"
            android:layout_height = "wrap_content"
            android:text = "Idle"
            android:textColor = "#47b8fd"
            android:textSize = "15dp"
            android:textAppearance = "?android:attr/textAppearanceMedium" />
        <TextView
            android:id = "@+id/tapToViewText"
            android:layout_width = "wrap_content"
            android:layout_height = "wrap_content"
            android:text = "Tap to view"
            android:textColor = "#ffffff"
            android:textSize = "15dp"
            android:layout_marginLeft = "20dp"
            android:layout_toRightOf = "@+id/idletext"
            android:textAppearance = "?android:attr/textAppearanceMedium" />
    </RelativeLayout>
</RelativeLayout>

child_layout:

    <?xml version = "1.0" encoding = "utf-8"?>
<LinearLayout xmlns:android = "http://schemas.android.com/apk/res/android"
    android:layout_width = "wrap_content"
    android:layout_height = "wrap_content"
    android:orientation = "vertical">
    <LinearLayout
        android:id = "@+id/form_layout"
        android:layout_width = "wrap_content"
        android:layout_height = "wrap_content"
        android:layout_marginTop = "30dp"
        android:layout_gravity = "center"
        android:background = "@android:color/white"
        android:orientation = "vertical">
        <LinearLayout
            android:id = "@+id/form_view_layout"
            android:layout_width = "137dp"
            android:layout_height = "178dp"
            android:orientation = "vertical"
            android:layout_marginTop = "3dp"
            android:layout_marginBottom = "3dp"
            android:layout_marginLeft = "3dp"
            android:layout_marginRight = "3dp"
            android:layout_gravity = "center"
            android:weightSum = "100"
            android:background = "@android:color/white">
            <ImageView
                android:src = "@drawable/image1"
                android:layout_width = "match_parent"
                android:layout_height = "0dp"
                android:layout_weight = "72"
                android:layout_gravity = "center"
                android:id = "@+id/form_Image" />
            <TextView
                android:text = "sometext"
                android:textAppearance = "?android:attr/textAppearanceSmall"
                android:layout_width = "match_parent"
                android:layout_height = "0dp"
                android:textColor = "#00ccff"
                android:textSize = "12dp"
                android:layout_marginLeft = "10dp"
                android:layout_marginBottom = "5dp"
                android:layout_weight = "18"
                android:id = "@+id/heading" />
            <TextView
                android:text = "sometext"
                android:textAppearance = "?android:attr/textAppearanceSmall"
                android:layout_width = "match_parent"
                android:layout_height = "0dp"
                android:textSize = "12dp"
                android:layout_weight = "10"
                android:layout_marginBottom = "10dp"
                android:textColor = "@android:color/black"
                android:layout_marginLeft = "10dp"
                android:id = "@+id/subHeading1" />
        </LinearLayout>
    </LinearLayout>
    <TextView
        android:text = "sometext"
        android:textAppearance = "?android:attr/textAppearanceSmall"
        android:layout_width = "match_parent"
        android:layout_height = "wrap_content"
        android:textColor = "@android:color/black"
        android:textSize = "13dp"
        android:layout_below = "@+id/form_view_layout"
        android:layout_marginTop = "10dp"
        android:layout_gravity = "center"
        android:gravity = "center"
        android:id = "@+id/subHeading2" />
    <TextView
        android:text = "14/01/1997 5:00"
        android:textAppearance = "?android:attr/textAppearanceSmall"
        android:layout_width = "match_parent"
        android:layout_height = "wrap_content"
        android:textColor = "#696969"
        android:textSize = "13dp"
        android:layout_below = "@+id/subHeading2"
        android:layout_marginTop = "7dp"
        android:layout_gravity = "center"
        android:gravity = "center"
        android:id = "@+id/formupdateddatetime" />
</LinearLayout>

Код активности и адаптера:

namespace FormSample.Activities
{
    [Activity(Label = "FormsActivity")]
    public class FormsActivity : BaseActivity
    {

        protected override int Layout => Resource.Layout.Forms;

        private FormModel _formModel;

        List<Form> formsList = new List<Form>();

        List<Form> formsListToDelete = new List<Form>();

        private bool _isMultiSelect;

        public override void OnBackPressed()
        {
            FinishAffinity();
        }

        public static Intent NewIntent(Context context)
        {
            try
            {

                var intent = new Intent(context, typeof(FormsActivity));           

                return intent;
            }
            catch (Exception exception)
            {

                return null;
            }
        }


        protected async override void FindViewElements()
        {
            try
            {


                _formModel = new FormModel()
                {
                    Form = FindViewById<GridView>(Resource.Id.form_gridView),
                    FormToolbar = FindViewById<Toolbar>(Resource.Id.formToolbar)
                };

                formsList = new List<Form>();

                var teamForms = new List<Form>();

                List<TeamlistResponse> _fromsListFromLocal = await LocalService.Instance.GetFormsCreatedInLocal();

                foreach (var form in _fromsListFromLocal)
                {
                    var localForm = ConvertTeamsListDtoToForm(form);

                    formsList.Add(localForm);
                }

                formsList = formsList.OrderByDescending(x => x.modified_timestamp).ToList();

                InitializeScreen();

                LoggingManager.Exit("MethodName:FindViewElements And ActivityName:FormsActivity");
            }
            catch (Exception exception)
            {
                LoggingManager.Error(exception, "FindViewElements", "FormsActivity");
            }
        }

        public void InitializeScreen()
        {
            try
            {
                LoggingManager.Enter("MethodName:InitializeScreen And ActivityName:FormsActivity");
                SetSupportActionBar(_formModel.FormToolbar);              
                GetListOfForms();
                LoggingManager.Exit("MethodName:InitializeScreen And ActivityName:FormsActivity");
            }
            catch (Exception exception)
            {
                LoggingManager.Error(exception, "InitializeScreen", "FormsActivity");
            }
        }

        private void GetListOfForms()
        {

              _formModel.Form.ItemClick += Form_Click;

              _formModel.Form.Adapter = new FormAdapter(formsList, this);

        }


        private async void Form_Click(Object sender, AdapterView.ItemClickEventArgs e)
        {
            try
            {


                    var selectedItem = formsList[e.Position];

                    if (selectedItem.Caption != "New Form" && selectedItem.id != null)
                    {
                        View selectedForm = e.View;
                        LinearLayout selectedFormLayout = selectedForm.FindViewById<LinearLayout>(Resource.Id.form_layout);
                        if (selectedItem.IsSelected)
                        {
                            selectedItem.IsSelected = false;                           
                            selectedFormLayout.SetBackgroundColor(Color.White);
                            formsListToDelete.Remove(selectedItem);
                        }
                        else
                        {
                            selectedItem.IsSelected = true;                           
                            selectedFormLayout.SetBackgroundResource(Resource.Drawable.Form_Border);
                            formsListToDelete.Add(selectedItem);
                        }
                    }

            }
            catch (Exception exception)
            {

            }
        }

    }

    public class Form
    {
        private bool _isSelected;


        public byte[] ImageResourceId { get; set; }

        public string Heading { get; set; }

        public string SubHeading { get; set; }

        public string Caption { get; set; }

        public string UpdatedFormDate { get; set; }

        public string id { get; set; }

        public bool IsSelected
        {

            get { return _isSelected; }
            set
            {
                _isSelected = value;
            }
        }

    }

    public class FormAdapter : BaseAdapter<Form>
    {
        private List<Form> formItems;

        private Activity context;

        public override Form this[int position]
        {
            get
            {
                return formItems[position];
            }
        }

        public override int Count => formItems.Count;

        public FormAdapter(List<Form> forms, Activity context) : base()
        {
            try
            {
                LoggingManager.Enter("ConstructorName:FormAdapter And ActivityName:FormsActivity");
                this.context = context;
                formItems = forms;
                LoggingManager.Exit("ConstructorName:FormAdapter And ActivityName:FormsActivity");
            }
            catch (Exception exception)
            {
                LoggingManager.Error(exception, "FormAdapter", "FormAdapter", "FormsActivity");
            }
        }

        public override int GetItemViewType(int position)
        {
            return position;
        }

        public override long GetItemId(int position)
        {
            try
            {              
                return position;

            }
            catch (Exception exception)
            {              
                return 0;
            }
        }

        public override View GetView(int position, View convertView, ViewGroup parent)
        {
            try
            {

                var form = formItems[position];
                View view = convertView;
                if (view == null)
                    view = context.LayoutInflater.Inflate(Resource.Layout.Forms_ChildLayout, null);

                var imageBitMap = BitmapFactory.DecodeByteArray(form.ImageResourceId, 0, form.ImageResourceId.Length);
                view.FindViewById<ImageView>(Resource.Id.form_Image).SetImageBitmap(imageBitMap);
                view.FindViewById<TextView>(Resource.Id.heading).Text = form.Heading;
                view.FindViewById<TextView>(Resource.Id.subHeading1).Text = form.SubHeading;
                view.FindViewById<TextView>(Resource.Id.subHeading2).Text = form.Caption;
                view.FindViewById<TextView>(Resource.Id.formupdateddatetime).Text = form.UpdatedFormDate;

                return view;

            }
            catch (Exception exception)
            {
                LoggingManager.Error(exception, "GetView", "FormsActivity");
                return null;
            }
        }
    }
}

Обжигая, я узнал, что зритель должен использовать, но, будучи новичком в xamarin.android, я не совсем понимаю, как это сделать. Пожалуйста, помогите в решении этой проблемы.

Это потому, что метод getview вызывается после прокрутки, и, следовательно, первый выбор элемента также выбирает элемент 3

FreakyAli 29.10.2018 07:20

Спасибо за ответ @ G.hakim, Подскажите, пожалуйста, как это решить.

sahithi 29.10.2018 07:22
0
2
70
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

By searching I came to know viewholder has to use, but being newbie in xamarin.android I am not really understanding how to do that

Вот и пытаюсь сделать для вас класс Holder. Это может вам помочь

Объявите класс FormHolder в том же файле FormAdapter со всеми элементами управления, которые есть в макете вашего элемента Forms_ChildLayout.

public class FormHolder : Java.Lang.Object
{
    public ImageView Form_Image { get; set; }
    public TextView Heading { get; set; }
    public TextView SubHeading1 { get; set; }
    public TextView SubHeading2 { get; set; }
    public TextView Formupdateddatetime { get; set; }
}

Это будет FormAdapter вашего GetView

public override View GetView(int position, View convertView, ViewGroup parent)
{
    var view = convertView;
    FormHolder holder = null;
    if (view != null)
    {
        holder = view.Tag as FormHolder;
    }
    if (holder == null)
    {
        holder = new FormHolder();
        view = context.LayoutInflater.Inflate(Resource.Layout.Forms_ChildLayout, parent, false);
        holder.Form_Image = (ImageView)view.FindViewById(Resource.Id.form_Image);
        holder.Heading = (TextView)view.FindViewById(Resource.Id.heading);
        holder.SubHeading1 = (TextView)view.FindViewById(Resource.Id.subHeading1);
        holder.SubHeading2 = (TextView)view.FindViewById(Resource.Id.subHeading2);
        holder.Formupdateddatetime = (TextView)view.FindViewById(Resource.Id.formupdateddatetime);

        holder.Form_Image.SetImageBitmap(imageBitMap);
        holder.Heading.Text= form.Heading;
        holder.SubHeading1.Text= form.SubHeading;
        holder.SubHeading2.Text = form.Caption;
        holder.Formupdateddatetime.Text = form.UpdatedFormDate;
    }
    return view;
}

Это способ сделать это, но есть другое решение - использовать RecyclerView. Я знаю, что ListView выполняет многие функции почти так же, как RecyclerView, но использование RecyclerView вынуждает вас использовать шаблон ViewHolder, и у вас больше никогда не будет этой проблемы. Я не говорю, что ваше решение неверно, потому что это определенно не так, но есть решение использовать RecyclerView :-)

Darwind 29.10.2018 11:51

@Darwind - Я согласен с вами, в этой конкретной ситуации RecyclerView был бы более точным. Это не смешивает элементы при прокрутке и более продвинуто, чем ListView.

R15 29.10.2018 12:33

Другие вопросы по теме