react-keyboard-avoiding-container
Version:
A React component that provides smooth keyboard interactions for mobile web apps, handling viewport adjustments, scroll behavior, and input field focus with a sticky footer layout
175 lines (131 loc) • 4.65 kB
Markdown
# React Keyboard Avoiding Container
A React component for web applications that handles mobile keyboard interactions gracefully, ensuring proper viewport adjustments and scroll behavior when the keyboard appears. Works fluently across modern browsers and devices.
https://www.npmjs.com/package/react-keyboard-avoiding-container
## Features
- 📱 Automatic keyboard height detection
- 🔄 Smooth scroll adjustments when keyboard appears
- 🎯 Auto-scrolls to focused input fields
- 📍 Maintains viewport stability
- 🔒 Prevents unwanted scrolling/bouncing
- 🎨 Clean, responsive layout with sticky footer
- 💪 TypeScript support
- ⚛️ Works with React 16.8+
## Installation
```bash
npm install react-keyboard-avoiding-container
# or
yarn add react-keyboard-avoiding-container
```
## Usage
```jsx
import { KeyboardAvoidingContainer } from "react-keyboard-avoiding-container";
function LoginForm() {
const bodyContent = (
<div>
<input type="text" placeholder="Username" />
<input type="password" placeholder="Password" />
</div>
);
const footerContent = <button>Login</button>;
return (
<KeyboardAvoidingContainer body={bodyContent} footer={footerContent} />
);
}
```
## Props
| Prop | Type | Description |
| -------- | ----------------- | ---------------------------------------- |
| `body` | `React.ReactNode` | Main content of the container |
| `footer` | `React.ReactNode` | Footer content that sticks to the bottom |
## Features in Detail
### Keyboard Handling
- Automatically detects keyboard height using `visualViewport` API
- Adjusts the viewport height when keyboard appears/disappears
- Prevents unwanted scrolling and viewport jumps
### Focus Management
- Automatically scrolls to focused input fields
- Ensures focused elements are visible above the keyboard
- Smooth scrolling animations for better UX
### Layout Control
- Fixed positioning to prevent page scrolling
- Sticky footer that remains visible
- Handles orientation changes gracefully
## Browser Support
The component uses the `visualViewport` API for optimal keyboard handling. For browsers that don't support this API, it falls back to `window.innerHeight`.
## Best Practices
1. Place all interactive elements (inputs, textareas) in the `body` prop
2. Keep action buttons (submit, cancel) in the `footer` prop
3. Use within mobile-focused layouts
4. Ensure parent containers don't interfere with fixed positioning
## Example
```tsx
import React, { useState } from "react";
import { KeyboardAvoidingContainer } from "react-keyboard-avoiding-container";
const LoginPage: React.FC = () => {
const [username, setUsername] = useState("");
const [password, setPassword] = useState("");
const handleLogin = () => {
console.log("Login attempt:", { username, password });
alert("Login clicked!");
};
const bodyContent = (
<div>
<h1 className="text-2xl font-bold mb-6 text-center">Login</h1>
<div className="flex flex-col space-y-4">
<div>
<label
htmlFor="username"
className="block text-sm font-medium text-gray-700 mb-1"
>
Username
</label>
<input
type="text"
id="username"
value={username}
onChange={(e) => setUsername(e.target.value)}
className="border rounded-lg w-full p-2"
placeholder="Enter your username"
/>
</div>
<div>
<label
htmlFor="password"
className="block text-sm font-medium text-gray-700 mb-1"
>
Password
</label>
<input
type="password"
id="password"
value={password}
onChange={(e) => setPassword(e.target.value)}
className="border rounded-lg w-full p-2"
placeholder="Enter your password"
/>
</div>
</div>
</div>
);
const footerContent = (
<button
onClick={handleLogin}
className="w-full bg-blue-500 text-white py-2 px-4 rounded-lg hover:bg-blue-600 transition-colors"
>
Login
</button>
);
return (
<KeyboardAvoidingContainer body={bodyContent} footer={footerContent} />
);
};
export default LoginPage;
```
Demo:
https://github.com/user-attachments/assets/bced1ff1-1140-4038-ba63-438c9784b9b5
## Contributing
Contributions are welcome! Please feel free to submit a Pull Request.
## License
ISC
## Support
If you have any questions or run into issues, please open an issue on GitHub.