Network Security Internet Technology Development Database Servers Mobile Phone Android Software Apple Software Computer Software News IT Information

In addition to Weibo, there is also WeChat

Please pay attention

WeChat public account

Shulou

How to realize the Simulation of Amazon Human-computer interaction menu in react

2025-01-15 Update From: SLTechnology News&Howtos shulou NAV: SLTechnology News&Howtos > Development >

Share

Shulou(Shulou.com)06/01 Report--

Xiaobian to share with you how to achieve the react version of the simulation Amazon human-computer interaction menu, I hope you have something to gain after reading this article, let's discuss it together!

Introduction to requirements

This article is all about web-side requirements

Refer to the menu effect on the left side of the home page of Amazon and Jingdong Mall to implement a react version of the component for business use.

Let's look at the effects of Amazon and Jingdong Mall:

Amazon mall

JD. Com

From the above effects we get our menu effect requirements:

When our mouse hovers over the left menu, the right side will display its corresponding submenu item.

When our mouse moves up and down the left menu, the left side can quickly switch to the corresponding submenu.

When we move the mouse at a certain tilt angle to the right, the mouse will pass through the other left menu, but will not perform the switch.

So far, we've got the situation right where we need it. And then we're going to have to implement our plan.

implementation scheme

To achieve our requirements, the complexity is mainly in how to achieve the above requirements 3. I won't talk about the basic switching effect between requirement 1 and requirement 2, but go directly to requirement 3.

Fulfilment of requirement 3

To achieve this, we need to record the mouse movement trajectory from left to right (from the left menu area to the right menu area), and then determine whether it is within a triangular area according to its movement trajectory. If it is, it will not be allowed to switch menus.

Let's look at a picture first:

P1: Start position of mouse

P2: Fixed point 1 of the left menu, maximum displacement point of the mouse in the left area

P3: Fixed point 2 of left menu, maximum displacement point of mouse in left area

M: End position of mouse movement in left menu

From the above diagram we can conclude:

If the mouse starts at P1, then when the mouse moves to the right area, the triangle area that the mouse may pass through is the triangle P1-P2-P3. Point M is the end position of the mouse. So we determine whether the mouse trajectory in the triangle can be.

partial logic code const [active, setActive] = useState(null) //Selected menu const [showSub, setShowSub] = useState(false) //Whether to display submenu let timeout = useRef(null) //Set delay timer, Prevent mouse movement to tab content toggling when menu passes let mouseLocs = useRef([]) //Record coordinate array when mouse moves let firstSlope = useRef(null) //Fixed point of menu bar 1, change according to menu bar and content position let secondSlope = useRef(null) //Fixed point of menu bar 2, Change according to menu bar and content location const refNavigation = useRef(null) const refNav = useRef(null) const refSubnav = useRef(null) /** * According to the position of the content bar relative to the menu bar, judge whether the point in the moving process is in the triangle or not * @param {Object} p1 Start Position * @param {Object} p2 Menu Bar Anchor Point 1 * @param {Object} p3 Menu Bar Anchor Point 2 * @param {Object} m End Position * @return {*} */ function proPosInTriangle(p1, p2, p3, m) { //mouse coordinate position at end let x = m.x, y = m.y, //Start mouse coordinates x1 = p1.x, y1 = p1.y, //Menu Bar Wrapper Top Right Corner Coordinates x2 = p2.x, y2 = p2.y, //lower right corner coordinates x3 = p3.x, y3 = p3.y, // (y2 - y1) / (x2 - x1) is the slope of a line connecting two coordinates //Because the formula for a straight line is y=kx+b; when the slope is the same, just compare //The difference between b1 and b2 shows that the point is in // (x1,y1),(x2,y2) which direction of the line //When r1 is greater than 0, it means that the point is on the right side of the line, and so on r1 = y - y1 - ((y2 - y1) / (x2 - x1)) * (x - x1), r2 = y - y2 - ((y3 - y2) / (x3 - x2)) * (x - x2), r3 = y - y3 - ((y1 - y3) / (x1 - x3)) * (x - x3), compare compare = r1 * r2 * r3

< 0 && r1 >

0 // 返回是否在三角形内的结果 return compare } /** * 获取元素相对于浏览器左上角的坐标位置,为正值 * @param element * @return {{x: Number, y: Number}} * @constructor */ function LocFromdoc(element) { const { x, y, width, height } = element.getBoundingClientRect() return { x: x, y: y, width, height, } } /** * 记录元素的位置信息 * @param element * @return {{top: *, topAndHeight: number, left: *, leftAndWidth: number}} */ function getInfo(element) { const location = LocFromdoc(element) return { top: location.y, topAndHeight: location.y + element.offsetHeight, // offsetHeight 元素的像素高度, 高度包含该元素的垂直内边距和边框,且是一个整数 left: location.x, leftAndWidth: location.x + element.offsetWidth, } } /** * 根据内容栏相对于菜单栏的位置, 返回菜单栏的固定点1,和固定点2,保存在this.firstSlope和this.secondSlope对象里 * 即 左侧菜单栏的右上角和右下角的位置 */ function ensureTriangleDots() { // 获取菜单栏的位置 const info = getInfo(refNav.current) const x1 = info.leftAndWidth const y1 = info.top const x2 = x1 const y2 = info.topAndHeight firstSlope.current = { x: x1, y: y1, } secondSlope.current = { x: x2, y: y2, } } const onMouseOver = useCallback( obj => { let diff try { // 是否在指定三角形内 diff = proPosInTriangle( mouseLocs.current[0], firstSlope.current, secondSlope.current, mouseLocs.current[2] ) } catch (ex) {} // 是就启动延迟显示, // 否则不延迟 if (diff) { timeout.current = setTimeout(() => { setActive(obj.key) setShowSub(true) }, 300) } else { setActive(obj.key) setShowSub(true) } }, [mouseLocs, timeout] ) const onMouseEnter = () => { // 计算位置 if (refNav.current) { ensureTriangleDots() } setShowSub(true) } // 移出菜单所在区域 const onMouseLeave = () => { if (refSubnav.current) { setActive(null) setShowSub(false) } } // 记录鼠标在菜单栏中移动的最后三个坐标位置 const onMousemove = event => { mouseLocs.current.push({ x: event.pageX, y: event.pageY, }) if (mouseLocs.current.length > 3) { // 移除超过三项的数据 mouseLocs.current.shift() } } // 鼠标移出的时候,清除延时器 const onMouseout = () => { if (timeout.current) { clearTimeout(timeout.current) } }实现效果

看完了这篇文章,相信你对"如何实现react版模拟亚马逊人机交互菜单"有了一定的了解,如果想了解更多相关知识,欢迎关注行业资讯频道,感谢各位的阅读!

Welcome to subscribe "Shulou Technology Information " to get latest news, interesting things and hot topics in the IT industry, and controls the hottest and latest Internet news, technology news and IT industry trends.

Views: 0

*The comments in the above article only represent the author's personal views and do not represent the views and positions of this website. If you have more insights, please feel free to contribute and share.

Share To

Development

Wechat

© 2024 shulou.com SLNews company. All rights reserved.

12
Report