8

I have an application where a user needs to press and hold a button to record audio. However, when a user holds the button on mobile, the browser tries to select nearby text (since the user is holding their finger down). It makes sense sorta, but I want to prevent this.

Alt Text

When I add user-select: none to the text, it no longer gets selected, but instead the text in the next level higher gets selected instead. Is there a way to completely capture this `user-select event on the button level and prevent it from bubbling to nearby text? I end up chasing the user-select: none event up my DOM tree at the moment and this doesn't feel correct.

Here's my button HTML:

<Button onMouseDown={onMouseDown} onMouseUp={onFinish} onMouseLeave={onFinish} className={classes.button} onTouchStart={onMouseDown} onTouchEnd={onFinish}>
            <div className="flex items-center relative">
                <svg height={radius * 2} width={radius * 2}>
                    <circle stroke="rgba(0,0,0,0.1)" fill="transparent" strokeWidth={stroke} r={normalizedRadius} cx={radius} cy={radius} transform={`rotate(-90 ${radius} ${radius})`} />
                    <circle
                        stroke="black"
                        fill="transparent"
                        strokeWidth={stroke}
                        strokeDasharray={circumference + ' ' + circumference}
                        style={{ strokeDashoffset }}
                        r={normalizedRadius}
                        cx={radius}
                        cy={radius}
                        transform={`rotate(-90 ${radius} ${radius})`}
                    />
                </svg>
                <Mic className="absolute" style={{
                    left: '50%',
                    top: '50%',
                    transform: 'translate(-50%, -50%)',
                    fontSize: '80px'
                }}/>
            </div>
        </Button>
        <div className="flex flex-col items-center justify-center px-3">
            <div className="font-bold mb-1 text-center">
                Click and hold to record your greeting.
            </div>
            <div className="text-center">(Max. 10 seconds)</div>
        </div>

onMouseDown or onTouchStart events trigger the event so I am wondering if I can utilize those events to "cancel" the user-select to prevent text outside of the button from being selected?

    const onMouseDown = async (e: React.MouseEvent | React.TouchEvent) => {
        onStart();
        setIsMicPressed(true)
    }

Thanks for any guidance!

3
  • have you tried this answer?
    – Rajiv
    Commented Feb 16, 2021 at 14:38
  • 1
    that's exactly what the user added as an answer below (and yes I have) Commented Feb 16, 2021 at 23:51
  • can set user-select: none to the body on onMouseDown event and undoing it onMouseUp event.
    – vaku
    Commented Apr 24 at 15:04

3 Answers 3

0

you can try to add this css:

.noselect {
  -webkit-touch-callout: none; /* iOS Safari */
    -webkit-user-select: none; /* Safari */
     -khtml-user-select: none; /* Konqueror HTML */
       -moz-user-select: none; /* Old versions of Firefox */
        -ms-user-select: none; /* Internet Explorer/Edge */
            user-select: none; /* Non-prefixed version, currently
                                  supported by Chrome, Edge, Opera and Firefox */
}

then you can add noselect class to the text

1
  • 2
    yea - that's what I added as stated in my question, but now it just selects text at the next dom level above Commented Feb 15, 2021 at 20:14
0

In this link you can see the solution for various browsers. just set css codes like this:W3schools

.prevent-select {
 -webkit-user-select: none; /* Safari */
  -ms-user-select: none; /* IE 10 and IE 11 */
  user-select: none; /* Standard syntax */
 }
1
  • 1
    This answer is already given
    – DarkBee
    Commented Apr 24 at 13:20
0

You could try putting * to select all the elements, then put the user-select styles:

* {
  -webkit-touch-callout: none; /* iOS Safari */
    -webkit-user-select: none; /* Safari */
     -khtml-user-select: none; /* Konqueror HTML */
       -moz-user-select: none; /* Old versions of Firefox */
        -ms-user-select: none; /* Internet Explorer/Edge */
            user-select: none; /* Non-prefixed version, currently
                                  supported by Chrome, Edge, Opera and Firefox */
}

You could also put this to the container holding the button and the other text you don't want selected:

container, container * {
  -webkit-touch-callout: none; /* iOS Safari */
    -webkit-user-select: none; /* Safari */
     -khtml-user-select: none; /* Konqueror HTML */
       -moz-user-select: none; /* Old versions of Firefox */
        -ms-user-select: none; /* Internet Explorer/Edge */
            user-select: none; /* Non-prefixed version, currently
                                  supported by Chrome, Edge, Opera and Firefox */
}

This would put ALL the elements in the DOM (or all the elements in the container) to no select, so you don't have to go to each element and put this style.

Not the answer you're looking for? Browse other questions tagged or ask your own question.