Merge branch 'main' of https://gitea.stretchy.ca/rick/jama
This commit is contained in:
48
.env.fcmtest-push
Normal file
48
.env.fcmtest-push
Normal file
@@ -0,0 +1,48 @@
|
||||
#** Required
|
||||
DB_PASSWORD=C@nuck2024
|
||||
JWT_SECRET=changemesupersecretjwtkey
|
||||
|
||||
#** App identity
|
||||
PROJECT_NAME=rosterchirp-dev
|
||||
APP_NAME=RosterChirp
|
||||
DEFCHAT_NAME=General Chat
|
||||
ADMIN_NAME=Admin User
|
||||
ADMIN_EMAIL=admin@rosterchirp.local
|
||||
ADMIN_PASS=Admin@1234
|
||||
ADMPW_RESET=false
|
||||
|
||||
#** Database
|
||||
# DB names intentionally kept as 'rosterchirp' — matches the existing live database
|
||||
DB_NAME=rosterchirp
|
||||
DB_USER=rosterchirp
|
||||
# DB_HOST and DB_PORT are set automatically in docker-compose (host=db, port=5432)
|
||||
|
||||
#** Tenancy mode
|
||||
# selfhost = single tenant (RosterChirp-Chat / RosterChirp-Brand / RosterChirp-Team)
|
||||
# host = multi-tenant (RosterChirp-Host only)
|
||||
APP_TYPE=host
|
||||
|
||||
#** RosterChirp-Host only (ignored in selfhost mode)
|
||||
HOST_DOMAIN=rosterchirp.com
|
||||
HOST_ADMIN_KEY=VBGFHEANTTGRDDWAASJKH
|
||||
|
||||
#** Optional
|
||||
PORT=3244
|
||||
TZ=America/Toronto
|
||||
|
||||
#** Firebase Cloud Messaging (FCM) — Android background push
|
||||
# Web app config — from Firebase Console → Project Settings → General → Your apps
|
||||
FIREBASE_API_KEY=AIzaSyAw1v4COZ68Po8CuwVKrQq0ygf7zFd2QCA
|
||||
FIREBASE_PROJECT_ID=fcmtest-push
|
||||
FIREBASE_MESSAGING_SENDER_ID=439263996034
|
||||
FIREBASE_APP_ID=1:439263996034:web:62a6a6b0afdbad99fdec9b
|
||||
# VAPID key — from Firebase Console → Project Settings → Cloud Messaging → Web Push certificates
|
||||
FIREBASE_VAPID_KEY=BE6hPKkbf-h0lUQ1tYo249pBOdZFFcWQn9suwg3NDwSE8C_hv8hk1dUY9zxHBQEChO_IAqyFZplF_SUb5c4Ofrw
|
||||
# Service account — from Firebase Console → Project Settings → Service accounts → Generate new private key
|
||||
FIREBASE_SERVICE_ACCOUNT={"type": "service_account", "project_id": "fcmtest-push", "private_key_id": "ddbf38d0c5f769b9b8b95000bf05c42b52bb58ad", "private_key": "-----BEGIN PRIVATE KEY-----\nMIIEvAIBADANBgkqhkiG9w0BAQEFAASCBKYwggSiAgEAAoIBAQDR4jqMb/0UPVpU\nctpVl9UWHY5lePR4hMEoodbRPofNQgtvx5HuFE61cVrquD8mfUmFB9eZc112KPyy\nMuuZHFkJrVT3iEhK8AoeJTNbxh+YiQvwMhyn9/KO4ntr/HIZxqHs62M46rqehZFS\nFR79zG1ptl/hRFkTTwQoQOOAdqP6gJuX+XpKpVeLPNCBVOAhfM8APA4dvjXUqhrk\ns+L5sH8xdttY/XFdjNhiUtv7uHuvww1hBKliUL6dDZZAlm3uwuYAdsvIHkDWOJ+B\nn8EE7n01h5PUpOihQ2poBAFGHvrT9ifk3bzuGviE74ejErCbBEBwJZvvsaebvaG4\n5dI3SQLXAgMBAAECggEAELX0d24LNmtUH9ktLRdzrdkYl1e0D0xynKuWEP7rjRov\nEu1O3yfaxHOMC5gz3vqmueLP9bXLwTauN/n57Cznoe+dDkBZkS3fgFrx5eK2bUys\nGKnEwlLpixrZPNXSt96q0dRECCoYRbrYwTJRT1/RblNI+wSYGwN1j0brVjUcBTvH\nPjpnt9bkIS+Rb1XJg1+TfQFzt1/WvFscpDpc7zUCGczgD7hAXJU2v2NYZyNtjn2g\niFD4r0AODuFk1Z6C8fbUsgcl8AXXQnJSLPTUXnyzifzBVQmGBu3HewLDHI99pTCZ\nT8aOwgaWYUWrjeg0jfyid08j14OfhE58/PuYGwcNsQKBgQDoh1R/OQ147D75BpXP\nEI1TyKTJNZiwnzRnP64cmzAwbIfc6w06hXTJGKIVqMBwM31R8WUfJ5cBxQOb1g3a\nZDgOTz4zO9M0mFyE/L0V3XrTXzCgPN+pCbZjcAw8oizF3u2rupM5lppxuXnkDiSi\nA2GuVdPR6M8pXUmNubs5XNe1jQKBgQDnEb21yF1K2IF9p1T0jcqLkzDLZDHHudVr\ndZSVVEyhpIFmBFgF8EC3C/ehA5i8Ar1K5JvcP5hpAH345QWOUUAKk000A4WpazZx\nfZM5Ema1xju1AFOSMDzwjt4N32Dg1VPqiLDT+CjiQFH67lSretO1IpS//IKT1Y+W\nOv3/ENfm8wKBgHt7moixUJE9zDdMovPCU3sB21iq6Loq4ZZO//RbCV091WyhOnYw\ndxNvzGt6IS+0eEGy0sOXr56V9FOmedbXT9lxhZOJmqCcpM1Otk9NPbPQIi+GBDRt\nXvkxgJ4WdXZi6449139Glh/8ollUlWmgKBh/pawcWR8bVjs4Pc+5mSflAoGAYfMm\nTRmrWl/evGojXCuC8ZmqdH17kKOY8Z19J7P9bAP1Ck7LFXFbrXx4Mxv4MbKjlUzF\nOR8IN3KK8+f5a/PLRvBcKLFZhpC5GnDV6LqBKYrnonmJ841ZN8wIGy9WvNgRY3kg\nJCqtAgOr/MfswmgluEH5dkzO+WXtIQzOwMHeE7sCgYAhrJV+PvnbnaIpfTaOKXGl\nsvzSXTuey5fQQLKMKsp2haKDVZ2hadDejRHsLJKVGb+KwdJ1s5WmBJ4L80/MnOKZ\n+9Yby9DKviVx0TbvMUGuAuWMl9syo4ICMVpp0cbeSOCM5/ulYjKSeU3sFKo7aWa9\nU8Pskm36I88orq90OBpWOg==\n-----END PRIVATE KEY-----\n","client_email": "firebase-adminsdk-fbsvc@fcmtest-push.iam.gserviceaccount.com", "client_id": "103917424542871804597", "auth_uri": "https://accounts.google.com/o/oauth2/auth", "token_uri": "https://oauth2.googleapis.com/token","auth_provider_x509_cert_url": "https://www.googleapis.com/oauth2/v1/certs", "client_x509_cert_url": "https://www.googleapis.com/robot/v1/metadata/x509/firebase-adminsdk-fbsvc%40fcmtest-push.iam.gserviceaccount.com", "universe_domain": "googleapis.com" }
|
||||
|
||||
RC_VERSION=latest
|
||||
|
||||
VAPID_SUBJECT=mailto:devpush@rosterchirp.com
|
||||
VAPID_PUBLIC=BGYS6vMY7zlx31UKRN9QcaOwfomoDJ50_MtfTcfE84q5bhTLq0rM1zSa6uzBTRBxZuFW1kMQP7ardN_jog3T14Y
|
||||
VAPID_PRIVATE=8SnDSEy_gs2jNwXLtOchZfHW0ppy_RG8wtvjSjYGA48
|
||||
66
docker-compose-fcmtest-push.yaml
Normal file
66
docker-compose-fcmtest-push.yaml
Normal file
@@ -0,0 +1,66 @@
|
||||
services:
|
||||
rosterchirp:
|
||||
image: rosterchirp-dev:${RC_VERSION:-latest}
|
||||
container_name: ${PROJECT_NAME:-rosterchirp}
|
||||
restart: unless-stopped
|
||||
ports:
|
||||
- "${PORT:-3000}:3000"
|
||||
environment:
|
||||
- NODE_ENV=production
|
||||
- TZ=${TZ:-UTC}
|
||||
- APP_TYPE=${APP_TYPE:-selfhost}
|
||||
- ADMIN_NAME=${ADMIN_NAME:-Admin User}
|
||||
- ADMIN_EMAIL=${ADMIN_EMAIL:-admin@rosterchirp.local}
|
||||
- ADMIN_PASS=${ADMIN_PASS:-Admin@1234}
|
||||
- ADMPW_RESET=${ADMPW_RESET:-false}
|
||||
- JWT_SECRET=${JWT_SECRET:-changeme_super_secret_jwt_key_2024}
|
||||
- APP_NAME=${APP_NAME:-rosterchirp}
|
||||
- DEFCHAT_NAME=${DEFCHAT_NAME:-General Chat}
|
||||
- DB_HOST=db
|
||||
- DB_PORT=5432
|
||||
- DB_NAME=${DB_NAME:-rosterchirp}
|
||||
- DB_USER=${DB_USER:-rosterchirp}
|
||||
- DB_PASSWORD=${DB_PASSWORD:?DB_PASSWORD is required}
|
||||
- HOST_DOMAIN=${HOST_DOMAIN:-}
|
||||
- HOST_ADMIN_KEY=${HOST_ADMIN_KEY:-}
|
||||
- FIREBASE_API_KEY=${FIREBASE_API_KEY:-}
|
||||
- FIREBASE_PROJECT_ID=${FIREBASE_PROJECT_ID:-}
|
||||
- FIREBASE_MESSAGING_SENDER_ID=${FIREBASE_MESSAGING_SENDER_ID:-}
|
||||
- FIREBASE_APP_ID=${FIREBASE_APP_ID:-}
|
||||
- FIREBASE_VAPID_KEY=${FIREBASE_VAPID_KEY:-}
|
||||
- FIREBASE_SERVICE_ACCOUNT=${FIREBASE_SERVICE_ACCOUNT}
|
||||
- VAPID_SUBJECT=${VAPID_SUBJECT:-mailto:push@rosterchirp.com}
|
||||
- VAPID_PUBLIC=${VAPID_PUBLIC:-CHANGEME}
|
||||
- VAPID_PRIVATE=${VAPID_PRIVATE:-CHANGEME}
|
||||
volumes:
|
||||
- rosterchirp_uploads:/app/uploads
|
||||
depends_on:
|
||||
db:
|
||||
condition: service_healthy
|
||||
healthcheck:
|
||||
test: ["CMD", "wget", "-q", "--spider", "http://localhost:3000/api/health"]
|
||||
interval: 30s
|
||||
timeout: 10s
|
||||
retries: 3
|
||||
|
||||
db:
|
||||
image: postgres:16-alpine
|
||||
container_name: ${PROJECT_NAME:-rosterchirp}_db
|
||||
restart: unless-stopped
|
||||
environment:
|
||||
- POSTGRES_DB=${DB_NAME:-rosterchirp}
|
||||
- POSTGRES_USER=${DB_USER:-rosterchirp}
|
||||
- POSTGRES_PASSWORD=${DB_PASSWORD:?DB_PASSWORD is required}
|
||||
volumes:
|
||||
- rosterchirp_db:/var/lib/postgresql/data
|
||||
healthcheck:
|
||||
test: ["CMD-SHELL", "pg_isready -U ${DB_USER:-rosterchirp} -d ${DB_NAME:-rosterchirp}"]
|
||||
interval: 5s
|
||||
timeout: 5s
|
||||
retries: 10
|
||||
|
||||
volumes:
|
||||
rosterchirp_db:
|
||||
driver: local
|
||||
rosterchirp_uploads:
|
||||
driver: local
|
||||
13
fcmtest-push-firebase-adminsdk-fbsvc-ddbf38d0c5.json
Normal file
13
fcmtest-push-firebase-adminsdk-fbsvc-ddbf38d0c5.json
Normal file
@@ -0,0 +1,13 @@
|
||||
{
|
||||
"type": "service_account",
|
||||
"project_id": "fcmtest-push",
|
||||
"private_key_id": "ddbf38d0c5f769b9b8b95000bf05c42b52bb58ad",
|
||||
"private_key": "-----BEGIN PRIVATE KEY-----\nMIIEvAIBADANBgkqhkiG9w0BAQEFAASCBKYwggSiAgEAAoIBAQDR4jqMb/0UPVpU\nctpVl9UWHY5lePR4hMEoodbRPofNQgtvx5HuFE61cVrquD8mfUmFB9eZc112KPyy\nMuuZHFkJrVT3iEhK8AoeJTNbxh+YiQvwMhyn9/KO4ntr/HIZxqHs62M46rqehZFS\nFR79zG1ptl/hRFkTTwQoQOOAdqP6gJuX+XpKpVeLPNCBVOAhfM8APA4dvjXUqhrk\ns+L5sH8xdttY/XFdjNhiUtv7uHuvww1hBKliUL6dDZZAlm3uwuYAdsvIHkDWOJ+B\nn8EE7n01h5PUpOihQ2poBAFGHvrT9ifk3bzuGviE74ejErCbBEBwJZvvsaebvaG4\n5dI3SQLXAgMBAAECggEAELX0d24LNmtUH9ktLRdzrdkYl1e0D0xynKuWEP7rjRov\nEu1O3yfaxHOMC5gz3vqmueLP9bXLwTauN/n57Cznoe+dDkBZkS3fgFrx5eK2bUys\nGKnEwlLpixrZPNXSt96q0dRECCoYRbrYwTJRT1/RblNI+wSYGwN1j0brVjUcBTvH\nPjpnt9bkIS+Rb1XJg1+TfQFzt1/WvFscpDpc7zUCGczgD7hAXJU2v2NYZyNtjn2g\niFD4r0AODuFk1Z6C8fbUsgcl8AXXQnJSLPTUXnyzifzBVQmGBu3HewLDHI99pTCZ\nT8aOwgaWYUWrjeg0jfyid08j14OfhE58/PuYGwcNsQKBgQDoh1R/OQ147D75BpXP\nEI1TyKTJNZiwnzRnP64cmzAwbIfc6w06hXTJGKIVqMBwM31R8WUfJ5cBxQOb1g3a\nZDgOTz4zO9M0mFyE/L0V3XrTXzCgPN+pCbZjcAw8oizF3u2rupM5lppxuXnkDiSi\nA2GuVdPR6M8pXUmNubs5XNe1jQKBgQDnEb21yF1K2IF9p1T0jcqLkzDLZDHHudVr\ndZSVVEyhpIFmBFgF8EC3C/ehA5i8Ar1K5JvcP5hpAH345QWOUUAKk000A4WpazZx\nfZM5Ema1xju1AFOSMDzwjt4N32Dg1VPqiLDT+CjiQFH67lSretO1IpS//IKT1Y+W\nOv3/ENfm8wKBgHt7moixUJE9zDdMovPCU3sB21iq6Loq4ZZO//RbCV091WyhOnYw\ndxNvzGt6IS+0eEGy0sOXr56V9FOmedbXT9lxhZOJmqCcpM1Otk9NPbPQIi+GBDRt\nXvkxgJ4WdXZi6449139Glh/8ollUlWmgKBh/pawcWR8bVjs4Pc+5mSflAoGAYfMm\nTRmrWl/evGojXCuC8ZmqdH17kKOY8Z19J7P9bAP1Ck7LFXFbrXx4Mxv4MbKjlUzF\nOR8IN3KK8+f5a/PLRvBcKLFZhpC5GnDV6LqBKYrnonmJ841ZN8wIGy9WvNgRY3kg\nJCqtAgOr/MfswmgluEH5dkzO+WXtIQzOwMHeE7sCgYAhrJV+PvnbnaIpfTaOKXGl\nsvzSXTuey5fQQLKMKsp2haKDVZ2hadDejRHsLJKVGb+KwdJ1s5WmBJ4L80/MnOKZ\n+9Yby9DKviVx0TbvMUGuAuWMl9syo4ICMVpp0cbeSOCM5/ulYjKSeU3sFKo7aWa9\nU8Pskm36I88orq90OBpWOg==\n-----END PRIVATE KEY-----\n",
|
||||
"client_email": "firebase-adminsdk-fbsvc@fcmtest-push.iam.gserviceaccount.com",
|
||||
"client_id": "103917424542871804597",
|
||||
"auth_uri": "https://accounts.google.com/o/oauth2/auth",
|
||||
"token_uri": "https://oauth2.googleapis.com/token",
|
||||
"auth_provider_x509_cert_url": "https://www.googleapis.com/oauth2/v1/certs",
|
||||
"client_x509_cert_url": "https://www.googleapis.com/robot/v1/metadata/x509/firebase-adminsdk-fbsvc%40fcmtest-push.iam.gserviceaccount.com",
|
||||
"universe_domain": "googleapis.com"
|
||||
}
|
||||
206
summary.md
Normal file
206
summary.md
Normal file
@@ -0,0 +1,206 @@
|
||||
# Mobile UI Fixes Summary
|
||||
**Date:** March 29, 2026
|
||||
**Version:** 0.12.45
|
||||
**Focus:** Android Chrome mobile browser issues
|
||||
|
||||
---
|
||||
|
||||
## 🎯 **Objective**
|
||||
Fix mobile UI issues in RosterChirp application on Android Chrome browser:
|
||||
1. Chrome autocomplete bar covering input fields
|
||||
2. Calendar popup appearing when selecting end time
|
||||
3. Time dropdowns being hidden by keyboard
|
||||
4. Inconsistent date/time row behavior
|
||||
|
||||
---
|
||||
|
||||
## 📁 **Files Modified**
|
||||
|
||||
### **Frontend Components**
|
||||
|
||||
#### **1. `frontend/src/components/SchedulePage.jsx`**
|
||||
**Changes Made:**
|
||||
- **TimeInput component:** Added `inputMode="text"` and `enterKeyHint="done"` to prevent calendar popup
|
||||
- **Form wrapper:** Changed from `autoComplete="new-password"` to `autoComplete="off"` for standard behavior
|
||||
- **Dropdown positioning:** Increased z-index from 300 to 9999 to prevent calendar interference
|
||||
- **Input attributes:** Added explicit `type="text"` and `inputMode="text"` for strong calendar prevention
|
||||
|
||||
**Lines Modified:** 187-222
|
||||
|
||||
#### **2. `frontend/src/components/MobileEventForm.jsx`**
|
||||
**Changes Made:**
|
||||
- **TimeInputMobile component:** Complete rewrite with intelligent positioning
|
||||
- **Visual Viewport API:** Added keyboard detection and dynamic positioning
|
||||
- **Smart dropdown logic:** Calculates available space above/below input
|
||||
- **Input attributes:** Added `inputMode="text"` and `enterKeyHint="done"`
|
||||
- **Z-index fix:** Increased to 9999 to prevent calendar interference
|
||||
- **End date/time row structure:** Fixed to match start date/time row
|
||||
|
||||
**Lines Modified:** 72-181, 554-568
|
||||
|
||||
#### **3. `frontend/src/components/UserManagerModal.jsx`**
|
||||
**Changes Made:**
|
||||
- **Form wrapper:** Added `autoComplete="off"` to suppress Chrome autocomplete
|
||||
- **Input consistency:** Ensured all inputs use standard autocomplete suppression
|
||||
|
||||
**Lines Modified:** 293-295
|
||||
|
||||
#### **4. `frontend/src/pages/GroupManagerPage.jsx`**
|
||||
**Changes Made:**
|
||||
- **Form wrapper:** Added `autoComplete="off"` for consistent behavior
|
||||
- **Input attributes:** Standardized autocomplete suppression
|
||||
|
||||
**Lines Modified:** 744-746
|
||||
|
||||
#### **5. `frontend/src/pages/UserManagerPage.jsx`**
|
||||
**Changes Made:**
|
||||
- **Form wrapper:** Added `autoComplete="off"` for mobile compatibility
|
||||
- **Input consistency:** Updated all input fields
|
||||
|
||||
**Lines Modified:** 624-626
|
||||
|
||||
#### **6. `frontend/src/index.css`**
|
||||
**Changes Made:**
|
||||
- **Cleaned up aggressive CSS:** Removed `-webkit-autofill` overrides that could affect iOS/desktop
|
||||
- **Reverted to standard:** Cross-browser compatible approach
|
||||
|
||||
**Lines Modified:** 35-62 (removed aggressive autocomplete CSS)
|
||||
|
||||
---
|
||||
|
||||
## 🔧 **Technical Solutions Implemented**
|
||||
|
||||
### **1. Chrome Autocomplete Suppression**
|
||||
```jsx
|
||||
// Standard approach (safe for all browsers)
|
||||
<input autoComplete="off" />
|
||||
<form autoComplete="off">
|
||||
```
|
||||
|
||||
### **2. Calendar Popup Prevention**
|
||||
```jsx
|
||||
// Strong signals to prevent date picker
|
||||
<input
|
||||
type="text"
|
||||
inputMode="text"
|
||||
enterKeyHint="done"
|
||||
autoComplete="off"
|
||||
/>
|
||||
```
|
||||
|
||||
### **3. Smart Dropdown Positioning**
|
||||
```js
|
||||
// Visual Viewport API for keyboard detection
|
||||
const handleViewportChange = () => {
|
||||
if (window.visualViewport) {
|
||||
const offset = window.innerHeight - window.visualViewport.height;
|
||||
setKeyboardOffset(offset > 0 ? offset : 0);
|
||||
}
|
||||
};
|
||||
|
||||
// Intelligent positioning based on available space
|
||||
const spaceAbove = rect.top;
|
||||
const spaceBelow = window.innerHeight - rect.bottom - keyboardOffset;
|
||||
|
||||
if (spaceBelow >= dropdownHeight) {
|
||||
setDropdownPosition({ top: '100%', bottom: 'auto' });
|
||||
} else {
|
||||
setDropdownPosition({ top: 'auto', bottom: '100%' });
|
||||
}
|
||||
```
|
||||
|
||||
### **4. Z-Index Hierarchy Fix**
|
||||
```jsx
|
||||
// Time dropdowns above all other UI elements
|
||||
zIndex: 9999
|
||||
```
|
||||
|
||||
### **5. Consistent Date/Time Row Structure**
|
||||
```jsx
|
||||
// Before (problematic)
|
||||
<div onClick={()=>setShowEndDate(true)} style={{cursor:'pointer'}}>
|
||||
<span>{date}</span>
|
||||
<TimeInputMobile />
|
||||
</div>
|
||||
|
||||
// After (fixed)
|
||||
<div>
|
||||
<span onClick={()=>setShowEndDate(true)} style={{cursor:'pointer'}}>{date}</span>
|
||||
<TimeInputMobile />
|
||||
</div>
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🐛 **Issues Resolved**
|
||||
|
||||
### **✅ Chrome Autocomplete Bar**
|
||||
- **Status:** Intended Chrome behavior (not a bug)
|
||||
- **Solution:** Standard `autoComplete="off"` implementation
|
||||
- **Result:** Consistent with Google Calendar's own behavior
|
||||
|
||||
### **✅ Calendar Popup on End Time**
|
||||
- **Root Cause:** Z-index conflict and row structure issues
|
||||
- **Solution:** Increased z-index + separate clickable areas
|
||||
- **Result:** Calendar only triggers on date click, not time click
|
||||
|
||||
### **✅ Keyboard Covering Dropdowns**
|
||||
- **Root Cause:** Fixed positioning without keyboard awareness
|
||||
- **Solution:** Visual Viewport API + intelligent positioning
|
||||
- **Result:** Dropdowns appear above keyboard or reposition automatically
|
||||
|
||||
### **✅ Inconsistent Date/Time Rows**
|
||||
- **Root Cause:** Different HTML structure between start/end rows
|
||||
- **Solution:** Made both rows structurally identical
|
||||
- **Result:** Consistent behavior for both date and time interactions
|
||||
|
||||
---
|
||||
|
||||
## 📱 **Cross-Browser Compatibility**
|
||||
|
||||
### **✅ iOS Safari**
|
||||
- Respects standard `autoComplete="off"`
|
||||
- No aggressive CSS overrides affecting behavior
|
||||
- Smart positioning works with Visual Viewport API
|
||||
|
||||
### **✅ Desktop Browsers**
|
||||
- Standard autocomplete behavior
|
||||
- No interference from mobile-specific fixes
|
||||
- Consistent time dropdown functionality
|
||||
|
||||
### **✅ Android Chrome**
|
||||
- Standard autocomplete suppression (as intended by Chrome)
|
||||
- Proper time dropdown positioning
|
||||
- No calendar interference with time selection
|
||||
|
||||
---
|
||||
|
||||
## 🎯 **Key Learnings**
|
||||
|
||||
1. **Chrome Android autocomplete is intended behavior**, not a bug
|
||||
2. **Even Google Calendar can't suppress it** - confirmed by user testing
|
||||
3. **Standard HTML attributes are the safest approach** for cross-browser compatibility
|
||||
4. **Visual Viewport API provides reliable keyboard detection**
|
||||
5. **Z-index hierarchy is critical** for preventing UI element conflicts
|
||||
6. **Consistent HTML structure prevents interaction conflicts**
|
||||
|
||||
---
|
||||
|
||||
## 📦 **Version History**
|
||||
- **0.12.38:** Initial autocomplete attempts
|
||||
- **0.12.39:** Aggressive CSS and JavaScript overrides
|
||||
- **0.12.40:** Cleaned up to standard approach
|
||||
- **0.12.41:** Fixed calendar z-index issues
|
||||
- **0.12.42:** Added smart dropdown positioning
|
||||
- **0.12.43:** Fixed date/time row structure
|
||||
- **0.12.44:** Refined positioning logic
|
||||
- **0.12.45:** Final stable implementation
|
||||
|
||||
---
|
||||
|
||||
## 🚀 **Ready for Deployment**
|
||||
All changes are cross-browser compatible and follow web standards. The implementation now:
|
||||
- Works consistently across iOS Safari, Android Chrome, and desktop browsers
|
||||
- Provides intelligent dropdown positioning
|
||||
- Maintains clean, maintainable code
|
||||
- Follows React best practices
|
||||
Reference in New Issue
Block a user