タグ D&D 時の表示位置修正 (#268) #400
@@ -57,7 +57,8 @@ const DraggableDroppableTagRow: FC<Props> = ({ tag, nestLevel, pathKey, parentTa
|
||||
isDragging: dragging } = useDraggable ({ id: dndId,
|
||||
data: { kind: 'tag',
|
||||
tagId: tag.id,
|
||||
parentTagId } })
|
||||
parentTagId,
|
||||
nestLevel } })
|
||||
|
||||
const { setNodeRef: setDropRef, isOver: over } = useDroppable ({
|
||||
id: dndId,
|
||||
@@ -90,18 +91,20 @@ const DraggableDroppableTagRow: FC<Props> = ({ tag, nestLevel, pathKey, parentTa
|
||||
e.stopPropagation ()
|
||||
}
|
||||
}}
|
||||
ref={node => {
|
||||
setDragRef (node)
|
||||
setDropRef (node)
|
||||
}}
|
||||
style={style}
|
||||
ref={setDropRef}
|
||||
className={cn (
|
||||
'min-w-0 max-w-full overflow-hidden rounded select-none',
|
||||
sp && 'touch-pan-y',
|
||||
over && 'ring-2 ring-offset-2')}
|
||||
{...attributes}
|
||||
{...listeners}>
|
||||
>
|
||||
<motion.div
|
||||
className="flex min-w-0 max-w-full items-baseline overflow-hidden"
|
||||
ref={setDragRef}
|
||||
style={style}
|
||||
className={cn (
|
||||
'inline-flex min-w-0 max-w-full items-baseline overflow-hidden',
|
||||
sp && 'touch-pan-y')}
|
||||
{...attributes}
|
||||
{...listeners}
|
||||
transition={{ layout: layoutTransition }}
|
||||
layoutId={animationMode === 'off'
|
||||
? undefined
|
||||
|
||||
@@ -2,6 +2,8 @@ import { DndContext,
|
||||
DragOverlay,
|
||||
MouseSensor,
|
||||
TouchSensor,
|
||||
pointerWithin,
|
||||
rectIntersection,
|
||||
useDroppable,
|
||||
useSensor,
|
||||
useSensors } from '@dnd-kit/core'
|
||||
@@ -183,6 +185,10 @@ type Props = {
|
||||
post: Post
|
||||
sp?: boolean }
|
||||
|
||||
type ActiveTagDrag = {
|
||||
tagId: number
|
||||
nestLevel: number }
|
||||
|
||||
|
||||
const TagDetailSidebar: FC<Props> = ({ className, post, sp }) => {
|
||||
sp = Boolean (sp)
|
||||
@@ -212,7 +218,7 @@ const TagDetailSidebar: FC<Props> = ({ className, post, sp }) => {
|
||||
return tagsTmp
|
||||
}, [post])
|
||||
|
||||
const [activeTagId, setActiveTagId] = useState<number | null> (null)
|
||||
const [activeTagDrag, setActiveTagDrag] = useState<ActiveTagDrag | null> (null)
|
||||
const [dragging, setDragging] = useState (false)
|
||||
const [saving, setSaving] = useState (false)
|
||||
const [tags, setTags] = useState (baseTags)
|
||||
@@ -328,9 +334,20 @@ const TagDetailSidebar: FC<Props> = ({ className, post, sp }) => {
|
||||
<TagSearch/>
|
||||
<DndContext
|
||||
sensors={sensors}
|
||||
collisionDetection={args => {
|
||||
const byPointer = pointerWithin (args)
|
||||
return byPointer.length > 0 ? byPointer : rectIntersection (args)
|
||||
}}
|
||||
onDragStart={e => {
|
||||
if (e.active.data.current?.kind === 'tag')
|
||||
setActiveTagId (e.active.data.current?.tagId ?? null)
|
||||
{
|
||||
const tagId = e.active.data.current?.tagId
|
||||
const nestLevel = e.active.data.current?.nestLevel
|
||||
setActiveTagDrag (
|
||||
tagId == null || nestLevel == null
|
||||
? null
|
||||
: { tagId, nestLevel })
|
||||
}
|
||||
setDragging (true)
|
||||
suppressClickRef.current = true
|
||||
document.body.style.userSelect = 'none'
|
||||
@@ -341,13 +358,13 @@ const TagDetailSidebar: FC<Props> = ({ className, post, sp }) => {
|
||||
suppressClickRef.current = false}, { capture: true, once: true })
|
||||
}}
|
||||
onDragCancel={() => {
|
||||
setActiveTagId (null)
|
||||
setActiveTagDrag (null)
|
||||
setDragging (false)
|
||||
document.body.style.userSelect = ''
|
||||
suppressClickRef.current = false
|
||||
}}
|
||||
onDragEnd={async e => {
|
||||
setActiveTagId (null)
|
||||
setActiveTagDrag (null)
|
||||
setDragging (false)
|
||||
await onDragEnd (e)
|
||||
document.body.style.userSelect = ''
|
||||
@@ -443,9 +460,11 @@ const TagDetailSidebar: FC<Props> = ({ className, post, sp }) => {
|
||||
|
||||
<DragOverlay adjustScale={false}>
|
||||
<div className="pointer-events-none">
|
||||
{activeTagId != null && (() => {
|
||||
const tag = findTag (tags, activeTagId)
|
||||
return tag && <TagLink tag={tag}/>
|
||||
{activeTagDrag != null && (() => {
|
||||
const tag = findTag (tags, activeTagDrag.tagId)
|
||||
return (
|
||||
tag
|
||||
&& <TagLink tag={tag} nestLevel={activeTagDrag.nestLevel}/>)
|
||||
}) ()}
|
||||
</div>
|
||||
</DragOverlay>
|
||||
|
||||
新しい課題から参照
ユーザをブロックする