This commit is contained in:
@@ -0,0 +1,21 @@
|
|||||||
|
import type { FC } from 'react'
|
||||||
|
|
||||||
|
type Props = {
|
||||||
|
userId: string
|
||||||
|
statusId: string }
|
||||||
|
|
||||||
|
|
||||||
|
export default (({ userId, statusId }: Props) => {
|
||||||
|
const now = (new Date).toLocaleDateString ()
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div>
|
||||||
|
<blockquote className="twitter-tweet">
|
||||||
|
<p lang="ja" dir="ltr">
|
||||||
|
Loading...
|
||||||
|
</p>
|
||||||
|
— <a href={`https://twitter.com/${ userId }?ref_src=twsrc%3Etfw`}>@{userId}</a> <a href={`https://twitter.com/${ userId }/status/${ statusId }?ref_src=twsrc%5Etfw`}>{now}</a>
|
||||||
|
</blockquote>
|
||||||
|
<script async src="https://platform.twitter.com/widgets.js" charSet="utf-8"/>
|
||||||
|
</div>)
|
||||||
|
}) satisfies FC<Props>
|
||||||
@@ -1,13 +1,6 @@
|
|||||||
import type { ReactNode } from 'react'
|
import type { FC, ReactNode } from 'react'
|
||||||
|
|
||||||
<<<<<<< Updated upstream
|
|
||||||
import type { FC } from 'react'
|
|
||||||
|
|
||||||
type Props = { children: React.ReactNode }
|
|
||||||
=======
|
|
||||||
|
|
||||||
type Props = { children: ReactNode }
|
type Props = { children: ReactNode }
|
||||||
>>>>>>> Stashed changes
|
|
||||||
|
|
||||||
|
|
||||||
export default (({ children }: Props) => (
|
export default (({ children }: Props) => (
|
||||||
|
|||||||
@@ -8,6 +8,7 @@ import PostList from '@/components/PostList'
|
|||||||
import TagDetailSidebar from '@/components/TagDetailSidebar'
|
import TagDetailSidebar from '@/components/TagDetailSidebar'
|
||||||
import NicoViewer from '@/components/NicoViewer'
|
import NicoViewer from '@/components/NicoViewer'
|
||||||
import PostEditForm from '@/components/PostEditForm'
|
import PostEditForm from '@/components/PostEditForm'
|
||||||
|
import TwitterEmbed from '@/components/TwitterEmbed'
|
||||||
import TabGroup, { Tab } from '@/components/common/TabGroup'
|
import TabGroup, { Tab } from '@/components/common/TabGroup'
|
||||||
import MainArea from '@/components/layout/MainArea'
|
import MainArea from '@/components/layout/MainArea'
|
||||||
import { Button } from '@/components/ui/button'
|
import { Button } from '@/components/ui/button'
|
||||||
@@ -17,8 +18,27 @@ import { cn } from '@/lib/utils'
|
|||||||
import NotFound from '@/pages/NotFound'
|
import NotFound from '@/pages/NotFound'
|
||||||
import ServiceUnavailable from '@/pages/ServiceUnavailable'
|
import ServiceUnavailable from '@/pages/ServiceUnavailable'
|
||||||
|
|
||||||
|
import type { FC } from 'react'
|
||||||
|
|
||||||
import type { Post, User } from '@/types'
|
import type { Post, User } from '@/types'
|
||||||
|
|
||||||
|
const PostEmbed: FC<{ post: Post }> = ({ post }: { post: Post }) => {
|
||||||
|
const url = new URL (post.url)
|
||||||
|
switch (url.hostname.split ('.').slice (-2).join ('.'))
|
||||||
|
{
|
||||||
|
case 'nicovideo.jp':
|
||||||
|
const [videoId] = url.pathname.match (/(?<=\/watch\/)[a-zA-Z0-9]+?(?=\/|$)/)!
|
||||||
|
return <NicoViewer id={videoId} width={640} height={360}/>
|
||||||
|
case 'twitter.com':
|
||||||
|
case 'x.com':
|
||||||
|
const [userId] = url.pathname.match (/(?<=\/)[^\/]+?(?=\/|$)/)!
|
||||||
|
const [statusId] = url.pathname.match (/(?<=\/status\/)\d+?(?=\/|$)/)!
|
||||||
|
return <TwitterEmbed userId={userId} statusId={statusId}/>
|
||||||
|
default:
|
||||||
|
return <img src={post.thumbnail} alt={post.url} className="mb-4 w-full"/>
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
type Props = { user: User | null }
|
type Props = { user: User | null }
|
||||||
|
|
||||||
|
|
||||||
@@ -77,10 +97,6 @@ export default ({ user }: Props) => {
|
|||||||
return <ServiceUnavailable/>
|
return <ServiceUnavailable/>
|
||||||
}
|
}
|
||||||
|
|
||||||
const url = post ? new URL (post.url) : null
|
|
||||||
const nicoFlg = url?.hostname.split ('.').slice (-2).join ('.') === 'nicovideo.jp'
|
|
||||||
const match = nicoFlg ? url.pathname.match (/(?<=\/watch\/)[a-zA-Z0-9]+?(?=\/|$)/) : null
|
|
||||||
const videoId = match?.[0] ?? ''
|
|
||||||
const viewedClass = (post?.viewed
|
const viewedClass = (post?.viewed
|
||||||
? 'bg-blue-600 hover:bg-blue-700'
|
? 'bg-blue-600 hover:bg-blue-700'
|
||||||
: 'bg-gray-500 hover:bg-gray-600')
|
: 'bg-gray-500 hover:bg-gray-600')
|
||||||
@@ -99,12 +115,7 @@ export default ({ user }: Props) => {
|
|||||||
{post
|
{post
|
||||||
? (
|
? (
|
||||||
<>
|
<>
|
||||||
{nicoFlg
|
<PostEmbed post={post}/>
|
||||||
? (
|
|
||||||
<NicoViewer id={videoId}
|
|
||||||
width={640}
|
|
||||||
height={360}/>)
|
|
||||||
: <img src={post.thumbnail} alt={post.url} className="mb-4 w-full"/>}
|
|
||||||
<Button onClick={changeViewedFlg}
|
<Button onClick={changeViewedFlg}
|
||||||
className={cn ('text-white', viewedClass)}>
|
className={cn ('text-white', viewedClass)}>
|
||||||
{post.viewed ? '閲覧済' : '未閲覧'}
|
{post.viewed ? '閲覧済' : '未閲覧'}
|
||||||
@@ -112,7 +123,7 @@ export default ({ user }: Props) => {
|
|||||||
<TabGroup>
|
<TabGroup>
|
||||||
<Tab name="関聯">
|
<Tab name="関聯">
|
||||||
{post.related.length > 0
|
{post.related.length > 0
|
||||||
? <PostList posts={post.related} />
|
? <PostList posts={post.related}/>
|
||||||
: 'まだないよ(笑)'}
|
: 'まだないよ(笑)'}
|
||||||
</Tab>
|
</Tab>
|
||||||
{['admin', 'member'].some (r => user?.role === r) && (
|
{['admin', 'member'].some (r => user?.role === r) && (
|
||||||
|
|||||||
Reference in New Issue
Block a user