diff --git a/src/app/molecules/message/Message.jsx b/src/app/molecules/message/Message.jsx
index 42344d7..7d3ee63 100644
--- a/src/app/molecules/message/Message.jsx
+++ b/src/app/molecules/message/Message.jsx
@@ -714,9 +714,9 @@ function getEditedBody(editedMEvent) {
}
function Message({
- mEvent, isBodyOnly, roomTimeline, focus, fullTime,
+ mEvent, isBodyOnly, roomTimeline,
+ focus, fullTime, isEdit, setEdit, cancelEdit,
}) {
- const [isEditing, setIsEditing] = useState(false);
const roomId = mEvent.getRoomId();
const { editedTimeline, reactionTimeline } = roomTimeline ?? {};
@@ -731,7 +731,7 @@ function Message({
const avatarSrc = mEvent.sender?.getAvatarUrl(initMatrix.matrixClient.baseUrl, 36, 36, 'crop') ?? null;
const edit = useCallback(() => {
- setIsEditing(true);
+ setEdit(eventId);
}, []);
const reply = useCallback(() => {
replyTo(senderId, mEvent.getId(), body);
@@ -788,7 +788,7 @@ function Message({
eventId={mEvent.replyEventId}
/>
)}
- {!isEditing && (
+ {!isEdit && (
)}
- {isEditing && (
+ {isEdit && (
{
if (newBody !== body) {
initMatrix.roomsInput.sendEditedMessage(roomId, mEvent, newBody);
}
- setIsEditing(false);
+ cancelEdit();
}}
- onCancel={() => setIsEditing(false)}
+ onCancel={cancelEdit}
/>
)}
{haveReactions && (
)}
- {roomTimeline && !isEditing && (
+ {roomTimeline && !isEdit && (
);
}
@@ -386,6 +397,8 @@ function RoomViewContent({ eventId, roomTimeline }) {
const timelineSVRef = useRef(null);
const timelineScrollRef = useRef(null);
const eventLimitRef = useRef(null);
+ const [editEventId, setEditEventId] = useState(null);
+ const cancelEdit = () => setEditEventId(null);
const readUptoEvtStore = useStore(roomTimeline);
const [onLimitUpdate, forceUpdateLimit] = useForceUpdate();
@@ -470,6 +483,42 @@ function RoomViewContent({ eventId, roomTimeline }) {
}
}, [newEvent]);
+ const listenKeyboard = useCallback((event) => {
+ if (event.ctrlKey || event.altKey || event.metaKey) return;
+ if (event.key !== 'ArrowUp') return;
+ if (navigation.isRawModalVisible) return;
+
+ if (document.activeElement.id !== 'message-textarea') return;
+ if (document.activeElement.value !== '') return;
+
+ const {
+ timeline: tl, activeTimeline, liveTimeline, matrixClient: mx,
+ } = roomTimeline;
+ const limit = eventLimitRef.current;
+ if (activeTimeline !== liveTimeline) return;
+ if (tl.length > limit.length) return;
+
+ const mTypes = ['m.text'];
+ for (let i = tl.length - 1; i >= 0; i -= 1) {
+ const mE = tl[i];
+ if (
+ mE.getSender() === mx.getUserId()
+ && mE.getType() === 'm.room.message'
+ && mTypes.includes(mE.getContent()?.msgtype)
+ ) {
+ setEditEventId(mE.getId());
+ return;
+ }
+ }
+ }, [roomTimeline]);
+
+ useEffect(() => {
+ document.body.addEventListener('keydown', listenKeyboard);
+ return () => {
+ document.body.removeEventListener('keydown', listenKeyboard);
+ };
+ }, [listenKeyboard]);
+
const handleTimelineScroll = (event) => {
const timelineScroll = timelineScrollRef.current;
if (!event.target) return;
@@ -535,7 +584,15 @@ function RoomViewContent({ eventId, roomTimeline }) {
const isFocus = focusId === mEvent.getId();
if (isFocus) jumpToItemIndex = itemCountIndex;
- tl.push(renderEvent(roomTimeline, mEvent, isNewEvent ? null : prevMEvent, isFocus));
+ tl.push(renderEvent(
+ roomTimeline,
+ mEvent,
+ isNewEvent ? null : prevMEvent,
+ isFocus,
+ editEventId === mEvent.getId(),
+ setEditEventId,
+ cancelEdit,
+ ));
itemCountIndex += 1;
}
if (roomTimeline.canPaginateForward() || limit.length < timeline.length) {