i have created a TextField in Flutter that behaves similar to the Slack text field:
- The TextField animates to full screen when swiped up and minimizes when swiped down.
- In its minimized state, the TextField dynamically adjusts its height based on the content, up to 5 lines. After 5 lines, it enables scrolling.
I'm using an AnimatedContainer to handle the animation. Everything works fine except when the content crosses 5 lines and the TextField starts scrolling. At this point, the swipe-up action to expand the TextField to full screen stops working.
this is my code for the function:
KeyboardVisibilityBuilder _getTextFieldContainer(BuildContext context) {
return KeyboardVisibilityBuilder(
builder: (context, isKeyboardVisible) {
return Stack(
children: [
SingleChildScrollView(
child: Container(
width: double.infinity,
decoration: BoxDecoration(
border:
Border.all(color: Get.isDarkMode ? darkGrey : lightGrey),
color: widget.backgroundColor,
borderRadius: const BorderRadius.only(
topLeft: Radius.circular(8), topRight: Radius.circular(8)),
),
child: Column(
mainAxisSize: MainAxisSize.min,
children: [
Padding(
padding: const EdgeInsets.only(left: 12, right: 12),
child: GestureDetector(
onVerticalDragUpdate: (details) {
if (details.delta.dy > 0) { // Swipe down
if (isFullScreen) {
toggleFullScreen(context);
}
}
else if (details.delta.dy < 0) { // Swipe up
if (!isFullScreen) {
toggleFullScreen(context);
}
}
},
child: AnimatedContainer(
duration: Duration(milliseconds: 500),
curve: Curves.easeInOut,
height: isFullScreen
? textFieldHeight
: null, // Set height to null when not in full screen
constraints: isFullScreen
? null
: BoxConstraints(
minHeight: bottomBarHeight,
maxHeight: 5 * bottomBarHeight), // Set constraints for dynamic height
child: IntrinsicHeight(
child: TextField(
focusNode: _textFieldFocusNode,
controller: _chatController.textEditingController.value,
minLines: 1,
maxLines: isFullScreen ? null : (isKeyboardVisible ? 5 : 1),
keyboardType: TextInputType.multiline,
textInputAction: TextInputAction.newline,
autocorrect: false,
cursorColor:
Get.isDarkMode ? Colors.white : primaryColor,
decoration: InputDecoration(
enabledBorder: const UnderlineInputBorder(
borderSide: BorderSide(color: Colors.transparent),
),
focusedBorder: InputBorder.none,
hintText: widget.submitType == SubmitType.view
? 'Have a question? Ask now!'
: 'Type here',
suffixIcon: isKeyboardVisible || isFullScreen
? null
: Row(
mainAxisSize: MainAxisSize.min,
children: [
Obx(() => _getSpeechToText()),
Obx(() => _getTextFieldSuffix()),
],
),
),
// Note: UI wont get updated with value without this setState, textEditingController will get updated.
onChanged: (value) {
setState(
() {},
);
},
),
))
)),
isKeyboardVisible
? _textFieldBottomBar(context)
: const SizedBox.shrink(),
],
)),
) ,
if (isKeyboardVisible || isFullScreen)
Positioned(
bottom: 0,
left: 0,
right: 0,
child: _textFieldBottomBar(context),
)]);
},
);
}
@override
Widget build(BuildContext context) {
return _getTextFieldContainer(context);
}
and this is for for swiping up and swiping down and setting the textFieldHeight for fullscreen:
double textFieldHeight = 50.0;
double bottomBarHeight = 50.0;
bool isFullScreen = false;
void toggleFullScreen(BuildContext context) {
setState(() {
isFullScreen = !isFullScreen;
double screenHeight = MediaQuery.of(context).size.height;
textFieldHeight = isFullScreen ? screenHeight - bottomBarHeight : 50.0;
});
}
How can I resolve this issue so when it is in scrolling mode the swipe up can work?