当键盘出现时滚动布局

7

当键盘出现并隐藏工具栏(FrameLayout)时,我的屏幕会重新调整到顶部,我只需要将聊天项目滚动到顶部并保持我的框架布局在顶部。我尝试了一些来自Google和SO的示例,但是没有帮助我。

<activity
        android:name=".screen.workshiftscreen.WorkShiftActivity"
        android:launchMode="singleTop"
        android:windowSoftInputMode="adjustPan"
        android:screenOrientation="portrait" />

我对片段布局进行了一些编辑后,如下所示:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout 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:background="?attr/bg_second"
    android:orientation="vertical">

    <FrameLayout
        android:id="@+id/title"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_alignParentTop="true"
        android:layout_marginBottom="@dimen/space_large_s"
        android:background="?attr/bg_main"
        android:padding="@dimen/space_small_m">

        <TextView
            *params* />

        <ImageView
            *params* />
    </FrameLayout>

    <android.support.v4.widget.SwipeRefreshLayout
        android:id="@+id/swipe_refresh_chat"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_above="@id/edit_bar"
        android:layout_below="@+id/title">

            <android.support.v7.widget.RecyclerView
                android:id="@+id/messages"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:paddingLeft="@dimen/space_medium_l"
                android:paddingRight="@dimen/space_medium_l"
                android:scrollbars="vertical" />
    </android.support.v4.widget.SwipeRefreshLayout>

    <LinearLayout
        android:id="@+id/edit_bar"
        android:layout_width="match_parent"
        android:layout_height="60dp"
        android:layout_alignParentBottom="true"
        android:orientation="vertical"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintRight_toRightOf="parent">

        <View
            *params* />

        <LinearLayout
            *params*>

            <EditText
                android:id="@+id/message_input"
                android:layout_width="0dp"
                android:layout_height="wrap_content"
                android:layout_gravity="center"
                android:layout_marginLeft="16dp"
                android:layout_marginRight="16dp"
                android:layout_weight="1"
                android:background="@android:color/transparent"
                android:hint="@string/prompt_message"
                android:imeActionId="@+id/send"
                android:imeActionLabel="@string/action_send"
                android:imeOptions="actionSend"
                android:maxLines="6"
                tools:ignore="Autofill,InvalidImeActionId,TextFields" />

            <ImageButton
                android:id="@+id/send_button"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_marginEnd="@dimen/space_small_l"
                android:background="@android:color/transparent"
                android:contentDescription="@string/action_send"
                android:src="@android:drawable/ic_menu_send" />

            <ImageButton
                android:id="@+id/bottom_buttom"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_marginEnd="@dimen/space_small_l"
                android:background="@android:color/transparent"
                android:contentDescription="@string/action_send"
                android:src="@drawable/down_active" />
        </LinearLayout>
    </LinearLayout>
</RelativeLayout>

还有一些详细的图片 截图:

截图 我怎样才能做到像那样呢? 输入图像描述


1
使用android:windowSoftInputMode="adjustResize",并将要滚动的内容放在Scrollview/NestedScrollView中,并使视图(您想要固定在底部的视图)在滚动下方对齐,并指定滚动在这些视图上方。 示例发布在答案部分。 - Vikas Borkar
1
我曾经遇到过同样的问题,非常重要的是要将android:layout_gravity="bottom"添加到scrollview容器中。 - Denis Fedak
@DenisFedak,你真是个天才!我被这个问题困扰了一整天,直到我看到了你的评论!对于其他处于同样困境的人:在ScrollView中包含的布局中添加gravity = bottom,因为gravity指示父级如何显示子级。 - AlexB
4个回答

4
请在manifest文件中为该活动使用android:windowSoftInputMode="adjustResize",并将您想要滚动的内容放在Scrollview/NestedScrollView中。使视图(您想要固定在底部的那些视图)位于滚动视图下方,并指定滚动视图在这些视图上方。
请参考以下示例,您可以根据自己的需求创建类似的布局。尝试理解它的工作原理,您可以使用RelativeLayout代替任何容器视图。
示例:(适用于Activity/Fragment布局)
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
   android:id="@+id/rlRoot"
   android:layout_width="match_parent"
   android:layout_height="match_parent">

<!--Scrollable view: RecyclerView, NestedScrollView, Webview etc-->
<ScrollView
    android:id="@+id/nsScroll"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:layout_above="@+id/btnNext">

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="vertical">
        .
        .
        .
        <AutoCompleteTextView
            android:id="@+id/etDob"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:imeOptions="actionDone"
            android:inputType="date"
            android:maxLines="1" />
        .
        .
        .
    </LinearLayout>
</ScrollView>

<!--Sticks at the bottom-->
<Button
    android:id="@+id/btnNext"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_alignParentBottom="true"
    android:textColor="@android:color/white" />


这并不会滚动到底部,它只是确保您的输入在屏幕上显示。 - Leonardo Rick

1

首先,您需要检测键盘的出现

boolean isKeyboardShowing = false;
void onKeyboardVisibilityChanged(boolean opened) {
    print("keyboard " + opened);
}

// ContentView is the root view of the layout of this activity/fragment    
contentView.getViewTreeObserver().addOnGlobalLayoutListener(
    new ViewTreeObserver.OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {

    Rect r = new Rect();
    contentView.getWindowVisibleDisplayFrame(r);
    int screenHeight = contentView.getRootView().getHeight();

    // r.bottom is the position above soft keypad or device button.
    // if keypad is shown, the r.bottom is smaller than that before.
    int keypadHeight = screenHeight - r.bottom;

    Log.d(TAG, "keypadHeight = " + keypadHeight);

    if (keypadHeight > screenHeight * 0.15) { // 0.15 ratio is perhaps enough to determine keypad height.
        // keyboard is opened
        if (!isKeyboardShowing) {
            isKeyboardShowing = true
        binding.scrollView.fullScroll(ScrollView.FOCUS_UP)
        }
    }
    else {
        // keyboard is closed
        if (isKeyboardShowing) {
            isKeyboardShowing = false
        binding.scrollView.fullScroll(ScrollView.FOCUS_UP)
        }
    }
}

});

当键盘出现时,将滚动条更改为顶部。


1
它救了我的一天... - shehzy

1
在清单文件中,使用`adjustResize`代替`adjustPan`。
<activity
    android:name=".screen.workshiftscreen.WorkShiftActivity"
    android:launchMode="singleTop"
    android:windowSoftInputMode="adjustResize"
    android:screenOrientation="portrait" />

这不太有帮助,聊天条目和框架布局隐藏在顶部后面。 - AlexS
3
使用相对布局,并将底部视图(编辑框和发送按钮)设置为 alignParentBottom="true"。 - Kajol Chaudhary
你知道如何使用RelativeLayout吗?你应该将你的头部设置为alightParentTop="true",底部视图设置为alightParentBottom="true",并将swiperefreshlayout设置在头部下方和页脚上方。 - Kajol Chaudhary
哦,抱歉,我现在会尝试一下。 - AlexS
抱歉,这对我没有帮助。 - AlexS
你改变了 android:windowSoftInputMode 以适应调整大小吗? 能否在 RelativeLayout 之后分享新视图? - Kajol Chaudhary

0

"adjustResize"

该活动的主窗口总是被调整大小以为屏幕上的软键盘腾出空间。

"adjustPan"

该活动的主窗口不会被调整大小以为屏幕上的软键盘腾出空间。相反,窗口的内容会自动平移,以便当前焦点永远不会被键盘遮挡,用户始终可以看到他们正在输入什么。这通常不如调整大小方便,因为用户可能需要关闭软键盘才能访问和与窗口中被遮挡的部分进行交互。

链接了解更多信息,并根据您的需求尝试不同的模式


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接