0

I'm having problems with the layout of a chat activity on android. I'm doing the tests in a simple application, to make it easier for you to understand.

This is the xml layout:

<androidx.constraintlayout.widget.ConstraintLayout 
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:ads="http://schemas.android.com/apk/res-auto"
    android:id="@+id/constraintMessage"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="@drawable/wallpaper">

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical"
        ads:layout_constraintBottom_toBottomOf="parent"
        ads:layout_constraintEnd_toEndOf="parent"
        ads:layout_constraintStart_toStartOf="parent"
        ads:layout_constraintTop_toTopOf="parent">

        <ListView
            android:id="@+id/listViewMessages"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:layout_weight="1"
            android:paddingTop="7dp" />

        <LinearLayout
            android:id="@+id/linearLayoutCaixaTexto"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_marginStart="5dp"
            android:layout_marginLeft="5dp"
            android:layout_marginTop="8dp"
            android:layout_marginEnd="5dp"
            android:layout_marginRight="5dp"
            android:layout_marginBottom="8dp"
            android:layout_weight="0"
            android:background="@drawable/fundo_mensagem_chat_branco"
            android:gravity="center_vertical"
            android:orientation="horizontal"
            android:paddingLeft="16dp">

            <EditText
                android:id="@+id/editMessage"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_weight="1"
                android:background="#00000000"
                android:cursorVisible="true"
                android:ems="10"
                android:hint="Type here..."
                android:imeOptions="actionDone"
                android:inputType="textPersonName"
                android:linksClickable="true"
                android:longClickable="true"
                android:maxLength="500"
                android:paddingRight="5dp"
                android:singleLine="true"
                android:soundEffectsEnabled="false"
                android:textColor="@android:color/black"
                android:textStyle="normal" />

            <ImageView
                android:id="@+id/imageViewSendMessage"
                android:layout_width="30dp"
                android:layout_height="30dp"
                android:layout_marginTop="8dp"
                android:layout_marginEnd="16dp"
                android:layout_marginRight="16dp"
                android:layout_marginBottom="8dp"
                ads:srcCompat="@drawable/ic_enviar_preto_24dp" />

        </LinearLayout>

    </LinearLayout>

</androidx.constraintlayout.widget.ConstraintLayout>

These are the problems, all with respect to the keyboard:

  1. When you click on EditText, the keyboard opens normally, fast. But when I add items to the listView (so that it fills the entire screen), when clicking on EditText, the keyboard takes a while to open, and also to hide, it gets a little stuck. This is a very annoying problem.

  2. When the keyboard opens, the background in ConstraintLayout is changed, you can see the difference in the images below. I would like the keyboard to be above the background, just like chat apps, when we put a background image of the conversation. The closest I got was putting "adjustNothing" in the windowSoftInputMode, but then the keyboard was over EditText and ListView.

enter image description here enter image description here

See, if I use "adjustPan" in windowSoftInputMode, this happens:

enter image description here

In short, I would like it to look like this:

  • The keyboard should open and hide quickly.
  • EditText must always be above the keyboard (this already happens).
  • The background image of the conversation should not be changed when opening the keyboard.

I recorded a short video so you can see the problem. Notice in the video that when there are no messages in the listView, the keyboard opens and closes fast, but when there are messages, it is slow, stuck. And also notice the background, when you open the keyboard it is changed. At the end of the video I recorded the same situation in another app, there you can see that the keyboard opens normally and the wallpaper is not changed.

Video: https://www.youtube.com/watch?v=DdMFufZ_Glg&feature=youtu.be

Other codes (if needed):

AndroidManifest:

<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.applicationtest">
    <application
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:roundIcon="@mipmap/ic_launcher_round"
        android:supportsRtl="true"
        android:theme="@style/AppTheme">
        <activity android:name=".MainActivity"
            android:label="Chat"
            android:screenOrientation="portrait"
            android:windowSoftInputMode="adjustResize|stateHidden">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>
</manifest>

MainActivity:

public class MainActivity extends AppCompatActivity {
    
    private List<Message> listMessages = new ArrayList<>();
    private EditText editMessage;
    private ImageView imageViewSendMessage;
    private MessageAdapter adapterMessages;
    private ListView listViewMessages;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        editMessage = findViewById(R.id.editMessage);
        imageViewSendMessage = findViewById(R.id.imageViewSendMessage);
        listViewMessages = findViewById(R.id.listViewMessages);

        adapterMessages = new MessageAdapter(listMessages, this);
        listViewMessages.setDividerHeight(0);
        listViewMessages.setTranscriptMode(ListView.TRANSCRIPT_MODE_NORMAL);
        listViewMessages.setAdapter(adapterMessages);

        imageViewSendMessage.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                if (!editMessage.getText().toString().isEmpty()) {

                    Message message = new Message();
                    message.setM(editMessage.getText().toString());
                    message.setDm("20/08/2022");
                    listMessages.add(message);
                    adapterMessages.notifyDataSetChanged();

                }
            }
        });

    }
}

Adapter Class:

public class MessageAdapter extends ArrayAdapter<Message> {

    private Context context;
    private List<Message> mensagens;

    public MessageAdapter(List<Message> list, Context c) {
        super(c, 0, list);
        this.context = c;
        this.mensagens = list;
    }

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

        Message message = mensagens.get(position);

        listItem = LayoutInflater.from(context).inflate(R.layout.adapter_msg_rement,parent,false);

        TextView textMensagem;
        TextView dataMensagem;

        textMensagem = listItem.findViewById(R.id.textMensagemTexto);
        dataMensagem = listItem.findViewById(R.id.dataMensagem);

        textMensagem.setText(message.getM());
        dataMensagem.setText(message.getDm());
        textMensagem.setTextColor(Color.parseColor("#000000"));

        return listItem;
    }

}
jvoaojvictor
  • 145
  • 1
  • 11

1 Answers1

0

ListView attempts to reuse view objects in order to improve performance and avoid a lag in response to user scrolls. To take advantage of this feature, check if the convertView provided to getView(...) is null before creating or inflating a new view object. See Making ListView Scrolling Smooth for more ways to ensure smooth user experience.

As mentioned above you should take care of the performance by using convertView I'm guessing that's what causing your "little stuck" issues.

As that said I would recommend using RecyclerView

About the background image - you can use adjustPan to push the whole layout above and avoid resizing the image (hope that this is what you wanted...)

Enjoy and Good Luck

  • Hello liad, thanks for the reply. I will study more about convertView and see if I can get something. About the background, I already tried to use the AdjustPan and it didn't work. I edited the question with a screenshot of the result. – jvoaojvictor Aug 26 '20 at 14:51
  • @jvoaojvictor no problem its very easy just follow the link above. and for the background issue try this [answer](https://stackoverflow.com/questions/4287473/software-keyboard-resizes-background-image-on-android) if it helps you know what to do :) – liad horovitz Aug 26 '20 at 15:37