Javascript-форум (https://javascript.ru/forum/)
-   Библиотеки/Тулкиты/Фреймворки (https://javascript.ru/forum/library-toolkit-framework/)
-   -   Работа с DOM useRef и философия реакта (https://javascript.ru/forum/library-toolkit-framework/82647-rabota-s-dom-useref-i-filosofiya-reakta.html)

jabbascript 06.06.2021 14:13

Работа с DOM useRef и философия реакта
 
Здравствуйте!!!
Кто может подсказать как обойти секцию в компоненте Node с useEffect, useRef(говорят эта связка противоречит философии реакта), но как тогда мне определить рутовый компонент в дереве и ноды которые являются последними? Как получать доступ к li без ref?
export const ShowTree = () => {
    const [tree, setTree] = useState([])
    console.log('rerender tree', tree)
 
    useEffect(() => {
        async function loadTree(){
            const response = await getTree()
            setTree(JSON.parse(response))
        }
        loadTree()
    }, [])
 
    return <Tree data={tree} />
 
}
 
 
const Node = ({node}) => {
    
    const hasChildrens = node.childrens ? true : false
    const classesNode = ['node','expandOpen']
    const nodeTag = React.useRef(null);
 
    const handleExpand = (e) => {
        e.stopPropagation()
         const target = e.target
         console.log('click', target)
    }
 
    useEffect(() => {
        const isRoot = nodeTag?.current?.parentNode?.parentNode.tagName !== 'LI' ? 
        nodeTag.current.classList.add('isRoot') : 
        null
        const isLast = nodeTag.current.nextSibling ? null : nodeTag.current.classList.add('isLast')
        console.log('next', nodeTag.current.nextSibling)
    }, [])
    
    return(
        <>
            <li
                ref={nodeTag}
                className={classesNode.join(' ')}
            >
                <div className="expand-container">
                    <div className="expand" onClick={handleExpand}></div>
                    <div className="content">{node.name}</div>
                </div>
                {
                    hasChildrens && (
                        <Tree data={node.childrens} />
                    )
                }
            </li>
        </>
    )
    
}
 
const Tree = ({data}) => {
    return(
        <>
            <ul className="tree-container">
                {
                    data?.map(el => {
                        return(
                            <Node node={el} />
                        )
                    })
                }
            </ul>
        </>
    )
    
}

ksa 22.06.2021 11:35

jabbascript, я как раз читаю про хуки и готов поучаствовать в твоей проблеме в качестве закрепления прочитанного материала. :)

Но пример, который ты выложил, не особо рабочий... :(
Предлагаю сделать некий рабочий пример и на нем все это опробовать.
Что в итоге ты хочешь сделать с этим списком?
Для чего хочешь применять useEffect()?

Т.е. я не до конца понял суть твоей проблемы и твои желания в этом примере... :(

ksa 22.06.2021 11:59

Вот, вполне себе, рабочий тестовый пример... На нем и можно будет потренироваться.
Чего ты в итоге хотел?

import React,{useState, useEffect} from 'react';
import ReactDOM from 'react-dom';
import './index.css';


 
const Node = ({node}) => {
    const childrens = node.childrens ? <Tree data={node.childrens} /> : ''
    const classesNode = ['node', 'expandOpen']
 
    const handleExpand = (e) => {
		e.stopPropagation()
		const target = e.target
		console.log('click', target)
    }
    
    return (
		<li	className={classesNode.join(' ')}>
			<div className="content" onClick={handleExpand}>{node.name}</div>
			{childrens}
		</li>
    )
    
}
const Tree = ({data}) => {
    return (
		<ul className="tree-container">
			{
				data.map(el => {
					return (
						<Node key={el.id} node={el} />
					)
				})
			}
		</ul>
    )
    
}
const ShowTree = () => {
    const [tree, setTree] = useState([])
    console.log('rerender tree', tree)
 
    useEffect(() => {
		setTimeout(() => setTree([
			{name: 'Item 0', id: 0},
			{
				name: 'Item 1', 
				id: 1,
				childrens: [
					{name: 'Item 1 0', id: '1, 0'},
					{name: 'Item 1 1', id: '1, 1'},
					{name: 'Item 1 2', id: '1, 2'},
				]
			},
			{name: 'Item 2', id: 2},
		]), 1000)
    }, [])
 
    return <Tree data={tree} />
 
}
 
ReactDOM.render(
	<ShowTree />,
	document.getElementById('root')
);

SuperZen 23.06.2021 12:18

видно, что товарищ пришел из jquery ) или из document.getElementById()...

Здесь надо понять ) что надо менять в памяти объект, чтобы что-то поменялось, а не делать изменения через DOM...

ksa 23.06.2021 14:56

Цитата:

Сообщение от SuperZen
Здесь надо понять ) что надо менять в памяти объект, чтобы что-то поменялось, а не делать изменения через DOM...

Вот и я удивился, т.к. не понятно с какими он проблемами столкнулся.
Реши поучаствовать, дабы поднять свой скилл. :D


Часовой пояс GMT +3, время: 09:30.