Migrating card detail to functional component
This commit is contained in:
parent
139d3f7762
commit
849a47e05f
1 changed files with 97 additions and 112 deletions
|
@ -1,6 +1,6 @@
|
||||||
// Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
|
// Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
|
||||||
// See LICENSE.txt for license information.
|
// See LICENSE.txt for license information.
|
||||||
import React from 'react'
|
import React, {useState, useRef, useEffect} from 'react'
|
||||||
import {FormattedMessage, injectIntl, IntlShape} from 'react-intl'
|
import {FormattedMessage, injectIntl, IntlShape} from 'react-intl'
|
||||||
|
|
||||||
import {BlockIcons} from '../../blockIcons'
|
import {BlockIcons} from '../../blockIcons'
|
||||||
|
@ -27,49 +27,35 @@ type Props = {
|
||||||
readonly: boolean
|
readonly: boolean
|
||||||
}
|
}
|
||||||
|
|
||||||
type State = {
|
const CardDetail = (props: Props): JSX.Element|null => {
|
||||||
title: string
|
const {cardTree} = props
|
||||||
}
|
const [title, setTitle] = useState(cardTree.card.title)
|
||||||
|
const titleRef = useRef<Editable>(null)
|
||||||
|
const titleValueRef = useRef(title)
|
||||||
|
titleValueRef.current = title
|
||||||
|
|
||||||
class CardDetail extends React.Component<Props, State> {
|
useEffect(() => {
|
||||||
private titleRef = React.createRef<Editable>()
|
if (!title) {
|
||||||
|
titleRef.current?.focus()
|
||||||
|
}
|
||||||
|
}, [])
|
||||||
|
|
||||||
shouldComponentUpdate(): boolean {
|
useEffect(() => {
|
||||||
return true
|
return () => {
|
||||||
|
if (titleValueRef.current !== cardTree?.card.title) {
|
||||||
|
mutator.changeTitle(card, titleValueRef.current)
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
}, [])
|
||||||
|
|
||||||
componentDidMount(): void {
|
|
||||||
if (!this.state.title) {
|
|
||||||
this.titleRef.current?.focus()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
componentWillUnmount(): void {
|
|
||||||
const {cardTree} = this.props
|
|
||||||
if (!cardTree) {
|
|
||||||
return
|
|
||||||
}
|
|
||||||
const {card} = cardTree
|
|
||||||
if (this.state.title !== card.title) {
|
|
||||||
mutator.changeTitle(card, this.state.title)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
constructor(props: Props) {
|
|
||||||
super(props)
|
|
||||||
this.state = {
|
|
||||||
title: props.cardTree.card.title,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
render() {
|
|
||||||
const {cardTree} = this.props
|
|
||||||
if (!cardTree) {
|
if (!cardTree) {
|
||||||
return null
|
return null
|
||||||
}
|
}
|
||||||
|
|
||||||
const {card, comments} = cardTree
|
const {card, comments} = cardTree
|
||||||
|
|
||||||
const icon = card.icon
|
// componentWillUnmount(): void {
|
||||||
|
// }
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
|
@ -77,9 +63,9 @@ class CardDetail extends React.Component<Props, State> {
|
||||||
<BlockIconSelector
|
<BlockIconSelector
|
||||||
block={card}
|
block={card}
|
||||||
size='l'
|
size='l'
|
||||||
readonly={this.props.readonly}
|
readonly={props.readonly}
|
||||||
/>
|
/>
|
||||||
{!this.props.readonly && !icon &&
|
{!props.readonly && !card.icon &&
|
||||||
<div className='add-buttons'>
|
<div className='add-buttons'>
|
||||||
<Button
|
<Button
|
||||||
onClick={() => {
|
onClick={() => {
|
||||||
|
@ -96,32 +82,32 @@ class CardDetail extends React.Component<Props, State> {
|
||||||
</div>}
|
</div>}
|
||||||
|
|
||||||
<Editable
|
<Editable
|
||||||
ref={this.titleRef}
|
ref={titleRef}
|
||||||
className='title'
|
className='title'
|
||||||
value={this.state.title}
|
value={title}
|
||||||
placeholderText='Untitled'
|
placeholderText='Untitled'
|
||||||
onChange={(title: string) => this.setState({title})}
|
onChange={(title: string) => setTitle(title)}
|
||||||
saveOnEsc={true}
|
saveOnEsc={true}
|
||||||
onSave={() => {
|
onSave={() => {
|
||||||
if (this.state.title !== this.props.cardTree.card.title) {
|
if (title !== props.cardTree.card.title) {
|
||||||
mutator.changeTitle(card, this.state.title)
|
mutator.changeTitle(card, title)
|
||||||
}
|
}
|
||||||
}}
|
}}
|
||||||
onCancel={() => this.setState({title: this.props.cardTree.card.title})}
|
onCancel={() => setTitle(props.cardTree.card.title)}
|
||||||
readonly={this.props.readonly}
|
readonly={props.readonly}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
{/* Property list */}
|
{/* Property list */}
|
||||||
|
|
||||||
<CardDetailProperties
|
<CardDetailProperties
|
||||||
boardTree={this.props.boardTree}
|
boardTree={props.boardTree}
|
||||||
cardTree={this.props.cardTree}
|
cardTree={props.cardTree}
|
||||||
readonly={this.props.readonly}
|
readonly={props.readonly}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
{/* Comments */}
|
{/* Comments */}
|
||||||
|
|
||||||
{!this.props.readonly &&
|
{!props.readonly &&
|
||||||
<>
|
<>
|
||||||
<hr/>
|
<hr/>
|
||||||
<CommentsList
|
<CommentsList
|
||||||
|
@ -138,17 +124,16 @@ class CardDetail extends React.Component<Props, State> {
|
||||||
|
|
||||||
<div className='CardDetail content fullwidth'>
|
<div className='CardDetail content fullwidth'>
|
||||||
<CardDetailContents
|
<CardDetailContents
|
||||||
cardTree={this.props.cardTree}
|
cardTree={props.cardTree}
|
||||||
readonly={this.props.readonly}
|
readonly={props.readonly}
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{!this.props.readonly &&
|
{!props.readonly &&
|
||||||
<CardDetailContentsMenu card={this.props.cardTree.card}/>
|
<CardDetailContentsMenu card={props.cardTree.card}/>
|
||||||
}
|
}
|
||||||
</>
|
</>
|
||||||
)
|
)
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export default injectIntl(CardDetail)
|
export default injectIntl(CardDetail)
|
||||||
|
|
Loading…
Reference in a new issue