21

In my app, I need to use

-webkit-overflow-scrolling: touch;

Because the scroll on iOS feels too "hard". But I need to hide the scrollbar.

I have something like this:

.container {
  -webkit-overflow-scrolling: touch;
}

.container::-webkit-scrollbar  {
    display: none;
    height: 0;
    width: 0;
}

Now the scroll feels very fluid, but I can still see the scroll bar...

2
  • 1
    The "Hacking with a parent" example here works in Safari on iOS 12.2 in the XCode simulator: output.jsbin.com/lohiga Commented May 17, 2019 at 9:01
  • My understanding is that they add some extra bottom padding so the horisontal scrollbar is pushed down. Then they stick it inside a wrapper element with a fixed height and overflow-y: hidden so that the scrollbar stays inside that hidden overflow. Commented May 17, 2019 at 9:08

8 Answers 8

17

As seen here: https://forum.webflow.com/t/how-do-i-hide-the-browser-scrollbar-from-appearing-when-a-user-scrolls/59643/5

::-webkit-scrollbar {
    display: none; // Safari and Chrome
}

seems to work.

Sign up to request clarification or add additional context in comments.

Comments

16

As of May 2020, this was the only solution that allowed me to hide the horizontal scrollbar on iOS Safari - including when the website is installed on the home screen as a PWA.

The idea is to make your container slightly higher than it needs to be with a padding-bottom, and to clip out that extra space where to scrollbar appears with clip-path.

Here is a snippet:

.scroll-container {
  width: 100%;
  padding-bottom: 30px;
  white-space: nowrap;
  overflow: auto;
  clip-path: inset(0 0 30px 0);
}

.item {
  display: inline-block;
  width: 150px;
  height: 300px;
  margin-right: 20px;
  background-color: #ddd;
  border-radius: 20px;
}
<div class="scroll-container">
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
</div>

This does have the disadvantage of adding extra space, which does push down the other elements below. This issue could be negated / prevented with a negative margin. It wouldn't be super clean, but it would work.

Ex.:

.scroll-container { margin-bottom: -30px; }

3 Comments

Agreed, unfortunately this is the only method that works on iOS. Some of the above methods work on desktop but not iOS as the OP mentioned
This is the right answer, everything else is not working.
As of Nov 2024 the ::-webkit-scrollbar hidden trick seems to be respected for horizontal scroll bars on iOS 18 (at least). Before that, yeah this trick is the only thing that worked reliably for me.
6

I just played with this CodePen and it seems that if you set the background-color to transparent for all three properties below (and in this example also remove box-shadows), the scrollbar is not visible at all:

#style-1::-webkit-scrollbar-track {
  //    -webkit-box-shadow: inset 0 0 6px rgba(0,0,0,.1);
  background-color: transparent;
}

#style-1::-webkit-scrollbar {
  background-color: transparent;
}

#style-1::-webkit-scrollbar-thumb {
  //    -webkit-box-shadow: inset 0 0 6px rgba(0,0,0,.3);
  background-color: transparent;
}

This was tested in Chrome Desktop, Chrome for Android, and iOS Safari (v8.4) on an iPhone 6+.

I would however recommend for user experience (usability/accessibility) to keep the scrollbar visible though, as even I, knowing what I was doing, got a bit confused when there was no scrollbar.

2 Comments

what ios version?
The CodePen no longer works on iPadOS as of today
5

As others have mentioned, this works:

.container ::-webkit-scrollbar {
    display: none;
}

It's probably a good idea to scope it to the parent container of the scrollbar you want to hide and not use it globally.

Comments

3

Just styling normal CSS and I don't know why it's working perfect...

.list {
    white-space: nowrap;
    overflow-x: scroll;
    padding-bottom: 15px;
    margin-bottom: -15px;
    -webkit-overflow-scrolling: touch;
}
.list .item {
    display: inline-block;
    width: 80%;
}

enter image description here

Comments

1

At the time of writing (2019) I think the only way to handle this to use overflow to hide the scrollbar.

/* box-sizing reset */

* {
  box-sizing: border-box;
}


/* 
   scroll container with overflow
   set to hidden
*/

.container {
  overflow: hidden;
  width: 80vw;
  height: 20vh;
  outline: 1px solid;
}


/*
   scroller overflowing the container by 2rem
   and a 2rem bottom padding to make content 
   match the container height
*/

.scroller {
  display: flex;
  height: calc(100% + 2rem);
  padding-bottom: 2rem;
  overflow-y: hidden;
  overflow-x: auto;
  -webkit-overflow-scrolling: touch;
  scroll-snap-type: x mandatory;
}


/*
  slides
*/

.slide {
  flex: 1 0 100%;
  scroll-snap-align: center;
  display: flex;
  justify-content: center;
  align-items: center;
}


/* just a bit of color */

.a {
  background: orangered;
}

.b {
  background: gold;
}

.c {
  background: olive;
}
<div class="container">
  <div class="scroller">
    <div class="slide a">A</div>
    <div class="slide b">B</div>
    <div class="slide c">C</div>
  </div>
</div>

Comments

1

I had trouble hiding the scrollbar on Safari (iPhone) and couldn’t find an answer, so here’s what worked for me.

What I’m Using:

  • React v18
  • iPhone 13 Mini (iOS 18.0.1)
  • Safari (Version based on iOS 18.0.1, as of 02/02/2025)

The Solution:

  • Target the #root element:
    In React apps, the main container is usually a div with id="root". In your main CSS file, add:

#root {overflow: hidden;}

This disables scrolling on the root container and removes any scrollbars it might create,

  • Set up a scrollable container with hidden scrollbars: Assign a custom class to the main container of the component that will be displayed on the screen (e.g., your Landing.js component).

    .main-container { overflow-y: auto; -webkit-overflow-scrolling: touch; }

    .main-container::-webkit-scrollbar { display: none; }

This container handles the scrolling while keeping the scrollbar hidden.

Below is an example of my React tree:

<App>
  <Routes>
    <Route>
      <Landing />
    </Route>
  </Routes>
</App>

Inside Landing.js:

  • Assign the .main-container class to the main div.

    < div className="main-container">
    < div className="inner-content">
    {/* Your content here. For example, I have a Hero section, About Us section, etc.. */}
    </ div>
    < /div>

Now, when the content height exceeds the screen height, it will scroll without showing the scrollbar.

I hope this helps anyone facing the same issue on Safari (iPhone)! If you're still stuck, reach out on IG @370zumaya.

Below is an example of my CSS code:

#root {
  /* Manually hide scrollbars */
  overflow: hidden; 
}

.main-container {
  overflow-y: auto; 
}

.inner-content {
  overflow-y: visible; 
}


.main-container::-webkit-scrollbar  {
  display: none; /* Chrome, Safari, Edge */
}

1 Comment

Please correctly format all code
-2
/* Hide all scrollbars on touch devices */
@media (hover: none) {

  /* Blink and WebKit based browsers */
  ::-webkit-scrollbar {
    display: none;
  }

  /* Firefox */
  * {
    scrollbar-width: none;
  }

}

1 Comment

Downvote is not mine. The syntax is wrong for a start. Its not obvious what it does. And part of it has already been suggested as an answer.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.