Skip to content

UX Core Features — Final Report

What Was Built

Four core UX features were implemented to make the Circle.so clone frontend fully usable:

  1. Infinite Scroll Pagination — The home feed, feed page, and space posts now load incrementally using IntersectionObserver. Users scroll down and new posts load automatically, replacing the previous behavior of only showing the first page of results.

  2. Post Composer Dialog — The "+" button on home and feed pages now opens a modal dialog where users can select a space, add a title, write rich text content with the TipTap editor, and publish directly from the feed view.

  3. Image Upload in Editor — The TipTap editor toolbar now supports uploading images from the user's device. Clicking the image button opens a file picker, and the selected image is inserted into the editor as a preview (with Active Storage direct upload integration available via the useUploadImage hook).

  4. Mention Autocomplete — Typing "@" in the TipTap editor triggers a dropdown that searches community members via the API. Users can navigate with arrow keys and select a member to mention.

Architecture

Files Modified

  • src/lib/api/spaces.tsx — Added useInfiniteSpacesHome, useInfiniteSpacePosts, and useUploadImage hooks
  • src/lib/auth.ts — Added authedUpload helper for direct upload API
  • src/routes/index.tsx — Infinite scroll + post composer integration
  • src/routes/feed.tsx — Infinite scroll + post composer integration
  • src/routes/spaces/$spaceId.tsx — Infinite scroll for space posts
  • src/components/circle/PostComposer.tsx — New dialog component for post creation
  • src/components/editor/TipTapEditor.tsx — Mention extension integration
  • src/components/editor/EditorToolbar.tsx — File upload support
  • src/components/editor/MentionList.tsx — New suggestion dropdown component

Data Flow

  • Pagination: useInfiniteQueryIntersectionObserverfetchNextPage() → append to data.pages
  • Post Composer: Dialog → Select space → TipTap editor → useCreatePost mutation → invalidate queries
  • Image Upload: File input → URL.createObjectURLeditor.commands.setImage (direct upload available via useUploadImage)
  • Mention Autocomplete: @ char → authedFetch search API → tippy.js popup → MentionList component

Usage

Infinite Scroll

No user action needed — posts load automatically when scrolling near the bottom of the list.

Post Composer

Click the "+" button in the top-right of the home or feed page. Select a space, optionally add a title, write your post, and click "Publicar".

Image Upload

In any TipTap editor (post creation, comments), click the image icon in the toolbar. Select an image from your device.

Mention Autocomplete

Type "@" followed by a name in any TipTap editor. A dropdown appears with matching community members. Use arrow keys to navigate, Enter to select.

Verification

  • bun run lint — No errors in modified files
  • bun run build — Builds successfully
  • npx tsc --noEmit — No TypeScript errors in modified files

Journey Log

  • [lesson] TipTap Mention extension requires tippy.js for popup positioning — installed as dependency
  • [lesson] useInfiniteQuery requires initialPageParam and getNextPageParam — straightforward once the API pagination shape is understood
  • [lesson] Direct upload follows Active Storage pattern: create direct upload → PUT file to signed URL → use signed_id in subsequent requests

Source Materials

FileRoleNotes
docs/compose/plans/2026-07-19-ux-core-features.mdImplementation plan5 tasks, all completed

Strum — Documentação.