* Remove the hackcheck for upgrades * Rename the PostEmbeds folder to match the codebase style * Updates to latest lex refactor * Update to use new bsky agent * Update to use api package's richtext library * Switch to upsertProfile * Add TextEncoder/TextDecoder polyfill * Add Intl.Segmenter polyfill * Update composer to calculate lengths by grapheme * Fix detox * Fix login in e2e * Create account e2e passing * Implement an e2e mocking framework * Don't use private methods on mobx models as mobx can't track them * Add tooling for e2e-specific builds and add e2e media-picker mock * Add some tests and fix some bugs around profile editing * Add shell tests * Add home screen tests * Add thread screen tests * Add tests for other user profile screens * Add search screen tests * Implement profile imagery change tools and tests * Update to new embed behaviors * Add post tests * Fix to profile-screen test * Fix session resumption * Update web composer to new api * 1.11.0 * Fix pagination cursor parameters * Add quote posts to notifications * Fix embed layouts * Remove youtube inline player and improve tap handling on link cards * Reset minimal shell mode on all screen loads and feed swipes (close #299) * Update podfile.lock * Improve post notfound UI (close #366) * Bump atproto packages
209 lines
4.2 KiB
TypeScript
209 lines
4.2 KiB
TypeScript
import {AppBskyEmbedRecord} from '@atproto/api'
|
|
import {RootStoreModel} from '../root-store'
|
|
import {makeAutoObservable} from 'mobx'
|
|
import {ProfileViewModel} from '../profile-view'
|
|
import {isObj, hasProp} from 'lib/type-guards'
|
|
import {PickedMedia} from 'lib/media/types'
|
|
|
|
export interface ConfirmModal {
|
|
name: 'confirm'
|
|
title: string
|
|
message: string | (() => JSX.Element)
|
|
onPressConfirm: () => void | Promise<void>
|
|
}
|
|
|
|
export interface EditProfileModal {
|
|
name: 'edit-profile'
|
|
profileView: ProfileViewModel
|
|
onUpdate?: () => void
|
|
}
|
|
|
|
export interface ServerInputModal {
|
|
name: 'server-input'
|
|
initialService: string
|
|
onSelect: (url: string) => void
|
|
}
|
|
|
|
export interface ReportPostModal {
|
|
name: 'report-post'
|
|
postUri: string
|
|
postCid: string
|
|
}
|
|
|
|
export interface ReportAccountModal {
|
|
name: 'report-account'
|
|
did: string
|
|
}
|
|
|
|
export interface CropImageModal {
|
|
name: 'crop-image'
|
|
uri: string
|
|
onSelect: (img?: PickedMedia) => void
|
|
}
|
|
|
|
export interface DeleteAccountModal {
|
|
name: 'delete-account'
|
|
}
|
|
|
|
export interface RepostModal {
|
|
name: 'repost'
|
|
onRepost: () => void
|
|
onQuote: () => void
|
|
isReposted: boolean
|
|
}
|
|
|
|
export interface ChangeHandleModal {
|
|
name: 'change-handle'
|
|
onChanged: () => void
|
|
}
|
|
|
|
export interface WaitlistModal {
|
|
name: 'waitlist'
|
|
}
|
|
|
|
export type Modal =
|
|
| ConfirmModal
|
|
| EditProfileModal
|
|
| ServerInputModal
|
|
| ReportPostModal
|
|
| ReportAccountModal
|
|
| CropImageModal
|
|
| DeleteAccountModal
|
|
| RepostModal
|
|
| ChangeHandleModal
|
|
| WaitlistModal
|
|
|
|
interface LightboxModel {}
|
|
|
|
export class ProfileImageLightbox implements LightboxModel {
|
|
name = 'profile-image'
|
|
constructor(public profileView: ProfileViewModel) {
|
|
makeAutoObservable(this)
|
|
}
|
|
}
|
|
|
|
export class ImagesLightbox implements LightboxModel {
|
|
name = 'images'
|
|
constructor(public uris: string[], public index: number) {
|
|
makeAutoObservable(this)
|
|
}
|
|
setIndex(index: number) {
|
|
this.index = index
|
|
}
|
|
}
|
|
|
|
export interface ComposerOptsPostRef {
|
|
uri: string
|
|
cid: string
|
|
text: string
|
|
author: {
|
|
handle: string
|
|
displayName?: string
|
|
avatar?: string
|
|
}
|
|
}
|
|
export interface ComposerOptsQuote {
|
|
uri: string
|
|
cid: string
|
|
text: string
|
|
indexedAt: string
|
|
author: {
|
|
handle: string
|
|
displayName?: string
|
|
avatar?: string
|
|
}
|
|
embeds?: AppBskyEmbedRecord.ViewRecord['embeds']
|
|
}
|
|
export interface ComposerOpts {
|
|
replyTo?: ComposerOptsPostRef
|
|
onPost?: () => void
|
|
quote?: ComposerOptsQuote
|
|
}
|
|
|
|
export class ShellUiModel {
|
|
darkMode = false
|
|
minimalShellMode = false
|
|
isDrawerOpen = false
|
|
isDrawerSwipeDisabled = false
|
|
isModalActive = false
|
|
activeModals: Modal[] = []
|
|
isLightboxActive = false
|
|
activeLightbox: ProfileImageLightbox | ImagesLightbox | undefined
|
|
isComposerActive = false
|
|
composerOpts: ComposerOpts | undefined
|
|
|
|
constructor(public rootStore: RootStoreModel) {
|
|
makeAutoObservable(this, {
|
|
serialize: false,
|
|
rootStore: false,
|
|
hydrate: false,
|
|
})
|
|
}
|
|
|
|
serialize(): unknown {
|
|
return {
|
|
darkMode: this.darkMode,
|
|
}
|
|
}
|
|
|
|
hydrate(v: unknown) {
|
|
if (isObj(v)) {
|
|
if (hasProp(v, 'darkMode') && typeof v.darkMode === 'boolean') {
|
|
this.darkMode = v.darkMode
|
|
}
|
|
}
|
|
}
|
|
|
|
setDarkMode(v: boolean) {
|
|
this.darkMode = v
|
|
}
|
|
|
|
setMinimalShellMode(v: boolean) {
|
|
this.minimalShellMode = v
|
|
}
|
|
|
|
openDrawer() {
|
|
this.isDrawerOpen = true
|
|
}
|
|
|
|
closeDrawer() {
|
|
this.isDrawerOpen = false
|
|
}
|
|
|
|
setIsDrawerSwipeDisabled(v: boolean) {
|
|
this.isDrawerSwipeDisabled = v
|
|
}
|
|
|
|
openModal(modal: Modal) {
|
|
this.rootStore.emitNavigation()
|
|
this.isModalActive = true
|
|
this.activeModals.push(modal)
|
|
}
|
|
|
|
closeModal() {
|
|
this.activeModals.pop()
|
|
this.isModalActive = this.activeModals.length > 0
|
|
}
|
|
|
|
openLightbox(lightbox: ProfileImageLightbox | ImagesLightbox) {
|
|
this.rootStore.emitNavigation()
|
|
this.isLightboxActive = true
|
|
this.activeLightbox = lightbox
|
|
}
|
|
|
|
closeLightbox() {
|
|
this.isLightboxActive = false
|
|
this.activeLightbox = undefined
|
|
}
|
|
|
|
openComposer(opts: ComposerOpts) {
|
|
this.rootStore.emitNavigation()
|
|
this.isComposerActive = true
|
|
this.composerOpts = opts
|
|
}
|
|
|
|
closeComposer() {
|
|
this.isComposerActive = false
|
|
this.composerOpts = undefined
|
|
}
|
|
}
|