admin管理员组

文章数量:1289412

In my code right now there's two sets of buttons. One controls the like, main area, and in one of the tabs for the main area it shows a box meant to hold an image. There's also an area to the side that switches with tabs.

For some reason, my second set of images causes the area to go blank, displaying nothing and removing the box. How do I fix this? Where did I go wrong? I honestly have no clue what's up with this.

I tried messing with the naming conventions and altering the javascript very lightly a few times, but, admittedly I don't know javascript much at all yet so there wasn't much I knew to do.

I'm guessing that I misplaced the tabs div in the HTML but I tried moving it around and it didn't change anything at all. I'm so lost on this I've spent two days getting no work done because I just don't know what's going on with the issue.

function Tabs(evt, tabName) {
  var i, tabcontent, tablinks;
  tabcontent = document.getElementsByClassName("tabcontent");
  for (i = 0; i < tabcontent.length; i++) {
    tabcontent[i].style.display = "none";
  }
  tablinks = document.getElementsByClassName("tablinks");
  for (i = 0; i < tablinks.length; i++) {
    tablinks[i].className = tablinks[i].className.replace(" active", "");
  }
  document.getElementById(tabName).style.display = "block";
  evt.currentTarget.className += " active";

}

document.getElementById("defaultOpen").click();
#wrapper {
  width: 100%;
  height: 100%;
  display: inline-block;
}

#main {
  color: red;
  background-color: pink;
  width: 52%;
  height: 30rem;
  margin-top: 3rem;
  margin-inline: auto;
  border: 6px solid;
  border-color: brown;
  border-radius: 15% / 38px;
  padding: 4px;
}

#content {
  color: rgb(0, 0, 0);
  background-color: beige;
  width: 96%;
  height: 27rem;
  position: relative;
  top: 1.4rem;
  margin-inline: auto;
  border: 4.5px solid brown;
  border-radius: 15% / 30px;
  overflow: auto;
  scrollbar-width: none;
}

#profileimage {
  background-color: pink;
  width: 16rem;
  height: 25rem;
  border: 2.5px solid brown;
  border-radius: 15% / 15px;
  position: relative;
  top: 0.4rem;
}

#references {
  color: red;
}

.flex-container {
  display: flex;
  flex-wrap: wrap;
  margin: 0 auto;
}

.box {
  flex-grow: 1;
  flex-shrink: 1;
  flex-basis: calc(25% - 10px);
  margin: 5px;
}

img {
  width: 100%;
}

.tab {
  position: relative;
  text-align: center;
  top: 4.5rem;
}

.tab button {
  background-color: burlywood;
  padding: 4px;
  width: 10rem;
  font-size: 1.8rem;
  border: 6px solid brown;
  border-radius: 10% / 8px;
  cursor: pointer;
  color: rgb(176, 103, 66);
}

.tab2 {
  position: absolute;
  text-align: center;
  top: 0.5rem;
  left: 22rem;
}

.tab2 button {
  background-color: burlywood;
  width: 8rem;
  font-size: 18px;
  border: 3.5px solid brown;
  border-radius: 10% / 8px;
  cursor: pointer;
  color: rgb(176, 103, 66);
}

.tab button:hover {
  background-color: rgb(191, 147, 89);
  color: rgb(144, 58, 32);
  border: 6px solid brown;
  border-radius: 10% / 8px;
}

.tab button:active {
  background-color: rgb(153, 73, 51);
  color: rgb(70, 21, 6);
  border: 4px solid brown;
  border-radius: 10% / 8px;
}

.tabcontent {
  display: none;
  padding: 6px 12px;
  border-top: none;
}
<div id="wrapper">
  <div class="tab">
    <button class="tablinks" onclick="Tabs(event, 'profile')" id="defaultOpen">Profile</button>
    <button class="tablinks" onclick="Tabs(event, 'ref')">Ref Sheet</button>
  </div>

  <div id="main">
    <div id="content">
      <div id="profile" class="tabcontent">
        <div id="profileimage"></div>
        <div class="tab2" id="buttons2">
          <button class="tablinks" onclick="Tabs(event, 'about')" id="defaultOpen">About</button>
          <button class="tablinks" onclick="Tabs(event, 'extra')">Extra</button>
        </div>
        <div id="about" class="tabcontent">hello</div>
      </div>
      <div id="ref" class="tabcontent">
        <div id="references" class="flex-container">
          <div class="box">
            <img src=".jpg">
          </div>
          <div class="box">
            <img src=".jpg">
          </div>
          <div class="box">
            <img src=".jpg">
          </div>
          <div class="box">
            <img src=".jpg">
          </div>
          <div class="box">
            <img src=".jpg">
          </div>
          <div class="box">
            <img src=".jpg">
          </div>
        </div>
      </div>
    </div>
  </div>
</div>

In my code right now there's two sets of buttons. One controls the like, main area, and in one of the tabs for the main area it shows a box meant to hold an image. There's also an area to the side that switches with tabs.

For some reason, my second set of images causes the area to go blank, displaying nothing and removing the box. How do I fix this? Where did I go wrong? I honestly have no clue what's up with this.

I tried messing with the naming conventions and altering the javascript very lightly a few times, but, admittedly I don't know javascript much at all yet so there wasn't much I knew to do.

I'm guessing that I misplaced the tabs div in the HTML but I tried moving it around and it didn't change anything at all. I'm so lost on this I've spent two days getting no work done because I just don't know what's going on with the issue.

function Tabs(evt, tabName) {
  var i, tabcontent, tablinks;
  tabcontent = document.getElementsByClassName("tabcontent");
  for (i = 0; i < tabcontent.length; i++) {
    tabcontent[i].style.display = "none";
  }
  tablinks = document.getElementsByClassName("tablinks");
  for (i = 0; i < tablinks.length; i++) {
    tablinks[i].className = tablinks[i].className.replace(" active", "");
  }
  document.getElementById(tabName).style.display = "block";
  evt.currentTarget.className += " active";

}

document.getElementById("defaultOpen").click();
#wrapper {
  width: 100%;
  height: 100%;
  display: inline-block;
}

#main {
  color: red;
  background-color: pink;
  width: 52%;
  height: 30rem;
  margin-top: 3rem;
  margin-inline: auto;
  border: 6px solid;
  border-color: brown;
  border-radius: 15% / 38px;
  padding: 4px;
}

#content {
  color: rgb(0, 0, 0);
  background-color: beige;
  width: 96%;
  height: 27rem;
  position: relative;
  top: 1.4rem;
  margin-inline: auto;
  border: 4.5px solid brown;
  border-radius: 15% / 30px;
  overflow: auto;
  scrollbar-width: none;
}

#profileimage {
  background-color: pink;
  width: 16rem;
  height: 25rem;
  border: 2.5px solid brown;
  border-radius: 15% / 15px;
  position: relative;
  top: 0.4rem;
}

#references {
  color: red;
}

.flex-container {
  display: flex;
  flex-wrap: wrap;
  margin: 0 auto;
}

.box {
  flex-grow: 1;
  flex-shrink: 1;
  flex-basis: calc(25% - 10px);
  margin: 5px;
}

img {
  width: 100%;
}

.tab {
  position: relative;
  text-align: center;
  top: 4.5rem;
}

.tab button {
  background-color: burlywood;
  padding: 4px;
  width: 10rem;
  font-size: 1.8rem;
  border: 6px solid brown;
  border-radius: 10% / 8px;
  cursor: pointer;
  color: rgb(176, 103, 66);
}

.tab2 {
  position: absolute;
  text-align: center;
  top: 0.5rem;
  left: 22rem;
}

.tab2 button {
  background-color: burlywood;
  width: 8rem;
  font-size: 18px;
  border: 3.5px solid brown;
  border-radius: 10% / 8px;
  cursor: pointer;
  color: rgb(176, 103, 66);
}

.tab button:hover {
  background-color: rgb(191, 147, 89);
  color: rgb(144, 58, 32);
  border: 6px solid brown;
  border-radius: 10% / 8px;
}

.tab button:active {
  background-color: rgb(153, 73, 51);
  color: rgb(70, 21, 6);
  border: 4px solid brown;
  border-radius: 10% / 8px;
}

.tabcontent {
  display: none;
  padding: 6px 12px;
  border-top: none;
}
<div id="wrapper">
  <div class="tab">
    <button class="tablinks" onclick="Tabs(event, 'profile')" id="defaultOpen">Profile</button>
    <button class="tablinks" onclick="Tabs(event, 'ref')">Ref Sheet</button>
  </div>

  <div id="main">
    <div id="content">
      <div id="profile" class="tabcontent">
        <div id="profileimage"></div>
        <div class="tab2" id="buttons2">
          <button class="tablinks" onclick="Tabs(event, 'about')" id="defaultOpen">About</button>
          <button class="tablinks" onclick="Tabs(event, 'extra')">Extra</button>
        </div>
        <div id="about" class="tabcontent">hello</div>
      </div>
      <div id="ref" class="tabcontent">
        <div id="references" class="flex-container">
          <div class="box">
            <img src="https://t3.ftcdn/jpg/03/45/05/92/360_F_345059232_CPieT8RIWOUk4JqBkkWkIETYAkmz2b75.jpg">
          </div>
          <div class="box">
            <img src="https://t3.ftcdn/jpg/03/45/05/92/360_F_345059232_CPieT8RIWOUk4JqBkkWkIETYAkmz2b75.jpg">
          </div>
          <div class="box">
            <img src="https://t3.ftcdn/jpg/03/45/05/92/360_F_345059232_CPieT8RIWOUk4JqBkkWkIETYAkmz2b75.jpg">
          </div>
          <div class="box">
            <img src="https://t3.ftcdn/jpg/03/45/05/92/360_F_345059232_CPieT8RIWOUk4JqBkkWkIETYAkmz2b75.jpg">
          </div>
          <div class="box">
            <img src="https://t3.ftcdn/jpg/03/45/05/92/360_F_345059232_CPieT8RIWOUk4JqBkkWkIETYAkmz2b75.jpg">
          </div>
          <div class="box">
            <img src="https://t3.ftcdn/jpg/03/45/05/92/360_F_345059232_CPieT8RIWOUk4JqBkkWkIETYAkmz2b75.jpg">
          </div>
        </div>
      </div>
    </div>
  </div>
</div>

Share Improve this question edited Feb 21 at 10:02 Rory McCrossan 338k41 gold badges320 silver badges351 bronze badges asked Feb 21 at 9:59 kurtiskurtis 135 bronze badges 2
  • 2 With your function, you are first hiding all tabs, and then you make the one with the ID passed in tabName visible again. So when you click on your about button, you are making #about visible again. But that element itself is contained within #profile - which you also hid first, but now aren't making visible again. – C3roe Commented Feb 21 at 10:08
  • Ohh that makes sense, do you know a good way to fix that? I'm not very good with functions and javascript right now. Maybe it could be a separate function using some kind of if statement (those exist in js I think?) that makes it show when profile is showing and is clicked on? I dunno. Maybe uhmm. There's probably an easier solution than that I am incredibly dense sometimes. – kurtis Commented Feb 21 at 10:20
Add a comment  | 

3 Answers 3

Reset to default 1

I had some issues with your nesting. I solved it by adding a wrapper and data attributes (data-target)

Also the code can be much simpler using toggle and delegation

Thanks to McCrossan for the :scope, that is useful

document.getElementById('wrapper').addEventListener('click', (e) => {
  const btn = e.target.closest('button.tablinks');
  if (!btn) return;
  
  const targetId = btn.dataset.target;
  const currentTab = document.getElementById(targetId);
  if (!currentTab) return;
  
  // Use the parent of the target tab as the container.
  const container = currentTab.parentElement;
  
  // Only toggle direct children of that container.
  container.querySelectorAll(':scope > .tabcontent').forEach(tab => {
    tab.classList.toggle('active', tab === currentTab);
  });
});
#wrapper {
  width: 100%;
  height: 100%;
  display: inline-block;
}

#main {
  color: red;
  background-color: pink;
  width: 52%;
  height: 30rem;
  margin-top: 3rem;
  margin-inline: auto;
  border: 6px solid;
  border-color: brown;
  border-radius: 15% / 38px;
  padding: 4px;
}

#content {
  color: rgb(0, 0, 0);
  background-color: beige;
  width: 96%;
  height: 27rem;
  position: relative;
  top: 1.4rem;
  margin-inline: auto;
  border: 4.5px solid brown;
  border-radius: 15% / 30px;
  overflow: auto;
  scrollbar-width: none;
}

#profileimage {
  background-color: pink;
  width: 16rem;
  height: 25rem;
  border: 2.5px solid brown;
  border-radius: 15% / 15px;
  position: relative;
  top: 0.4rem;
}

#references {
  color: red;
}

.flex-container {
  display: flex;
  flex-wrap: wrap;
  margin: 0 auto;
}

.box {
  flex-grow: 1;
  flex-shrink: 1;
  flex-basis: calc(25% - 10px);
  margin: 5px;
}

img {
  width: 100%;
}

.tab {
  position: relative;
  text-align: center;
  top: 4.5rem;
}

.tab button {
  background-color: burlywood;
  padding: 4px;
  width: 10rem;
  font-size: 1.8rem;
  border: 6px solid brown;
  border-radius: 10% / 8px;
  cursor: pointer;
  color: rgb(176, 103, 66);
}

.tab2 {
  position: absolute;
  text-align: center;
  top: 0.5rem;
  left: 22rem;
}

.tab2 button {
  background-color: burlywood;
  width: 8rem;
  font-size: 18px;
  border: 3.5px solid brown;
  border-radius: 10% / 8px;
  cursor: pointer;
  color: rgb(176, 103, 66);
}

.tab button:hover {
  background-color: rgb(191, 147, 89);
  color: rgb(144, 58, 32);
  border: 6px solid brown;
  border-radius: 10% / 8px;
}

.tab button:active {
  background-color: rgb(153, 73, 51);
  color: rgb(70, 21, 6);
  border: 4px solid brown;
  border-radius: 10% / 8px;
}

.tabcontent {
  padding: 6px 12px;
  border-top: none;
  display: none;
}

.tabcontent.active {
  display: block;
}
<div id="wrapper">
  <!-- Outer tabs -->
  <div class="tab">
    <button class="tablinks active" data-target="profile">Profile</button>
    <button class="tablinks" data-target="ref">Ref Sheet</button>
  </div>

  <div id="main">
    <div id="content">
      <!-- Outer tab content: Profile -->
      <div id="profile" class="tabcontent active">
        <div id="profileimage"></div>
        <!-- Inner tab buttons -->
        <div class="tab2" id="buttons2">
          <button class="tablinks active" data-target="about">About</button>
          <button class="tablinks" data-target="extra">Extra</button>
        </div>
        <!-- Wrap inner tab content in its own container -->
        <div class="inner-tab-container">
          <div id="about" class="tabcontent active">About</div>
          <div id="extra" class="tabcontent">Extra content</div>
        </div>
      </div>

      <!-- Outer tab content: Ref Sheet -->
      <div id="ref" class="tabcontent">
        <div id="references" class="flex-container">
          <div class="box">
            <img src="https://t3.ftcdn/jpg/03/45/05/92/360_F_345059232_CPieT8RIWOUk4JqBkkWkIETYAkmz2b75.jpg">
          </div>
          <!-- (other image boxes) -->
        </div>
      </div>
    </div>
  </div>
</div>

C3roe is right. You need to limit the scope of Tabs function to correct the tab buttons. Because your Tabs function hides all .tabcontent elements when a button is clicked, it affects both sets of tabs (main area and sub-tabs).

TABS function

function Tabs(evt, tabName, containerId) {
  var i, tabcontent, tablinks;
  var container = document.getElementById(containerId);

  if (!container) return; // Prevent errors if the container doesn't exist

  tabcontent = container.getElementsByClassName("tabcontent");
  for (i = 0; i < tabcontent.length; i++) {
    tabcontent[i].style.display = "none";
  }

  tablinks = container.getElementsByClassName("tablinks");
  for (i = 0; i < tablinks.length; i++) {
    tablinks[i].className = tablinks[i].className.replace(" active", "");
  }

  document.getElementById(tabName).style.display = "block";
  evt.currentTarget.className += " active";
}

// Ensure only the main tabs are opened initially
document.getElementById("defaultOpen").click();

update the onclick events

<!-- Main Tabs -->
<button class="tablinks" onclick="Tabs(event, 'profile', 'content')" id="defaultOpen">Profile</button>
<button class="tablinks" onclick="Tabs(event, 'ref', 'content')">Ref Sheet</button>

<!-- Sub-tabs inside "profile" -->
<div class="tab2" id="buttons2">
  <button class="tablinks" onclick="Tabs(event, 'about', 'profile')">About</button>
  <button class="tablinks" onclick="Tabs(event, 'extra', 'profile')">Extra</button>
</div>

The main issue in your logic is that you have two separate tab toggle/content instances, yet your logic is clearing all of them when any of the links are clicked. You need to separate the tab logic so that only the tabs related to the clicked button is affected.

There's also some other issues in your code which need to be addressed:

  • Don't use onclick. It's no longer good practice. Bind event listeners in JS using addEventListener() instead.
  • Use data attributes to store element metadata instead of having parameters in a function reference in an onclick attribute
  • You have duplicated id attributes, which is invalid HTML. Use a common class when you need to apply the same behaviour to multiple elements.
  • Don't edit classes as strings of the attribute. Use the classList object instead. This has methods which allow you to add/remove/toggle classes as required.

With that said, here's a working example with the above changes made:

const tablinks = document.querySelectorAll('.tablinks');

const toggleTab = e => {
  const tabId = e.target.dataset.targettab;
  const targetTab = document.querySelector(`#${tabId}`);
  targetTab.parentElement.querySelectorAll(':scope > .tabcontent').forEach(tab => tab.classList.remove('show')); // hide sibling tabs
  targetTab.classList.add('show'); // display target tab
}

tablinks.forEach(tab => tab.addEventListener('click', toggleTab));

document.querySelectorAll(".defaultOpen").forEach(el => el.click());
#wrapper {
  width: 100%;
  height: 100%;
  display: inline-block;
}

#main {
  color: red;
  background-color: pink;
  width: 52%;
  height: 30rem;
  margin-top: 3rem;
  margin-inline: auto;
  border: 6px solid;
  border-color: brown;
  border-radius: 15% / 38px;
  padding: 4px;
}

#content {
  color: rgb(0, 0, 0);
  background-color: beige;
  width: 96%;
  height: 27rem;
  position: relative;
  top: 1.4rem;
  margin-inline: auto;
  border: 4.5px solid brown;
  border-radius: 15% / 30px;
  overflow: auto;
  scrollbar-width: none;
}

#profileimage {
  background-color: pink;
  width: 16rem;
  height: 25rem;
  border: 2.5px solid brown;
  border-radius: 15% / 15px;
  position: relative;
  top: 0.4rem;
}

#references {
  color: red;
}

.flex-container {
  display: flex;
  flex-wrap: wrap;
  margin: 0 auto;
}

.box {
  flex-grow: 1;
  flex-shrink: 1;
  flex-basis: calc(25% - 10px);
  margin: 5px;
}

img {
  width: 100%;
}

.tab {
  position: relative;
  text-align: center;
  top: 4.5rem;
}

.tab button {
  background-color: burlywood;
  padding: 4px;
  width: 10rem;
  font-size: 1.8rem;
  border: 6px solid brown;
  border-radius: 10% / 8px;
  cursor: pointer;
  color: rgb(176, 103, 66);
}

.tab2 {
  position: absolute;
  text-align: center;
  top: 0.5rem;
  left: 22rem;
}

.tab2 button {
  background-color: burlywood;
  width: 8rem;
  font-size: 18px;
  border: 3.5px solid brown;
  border-radius: 10% / 8px;
  cursor: pointer;
  color: rgb(176, 103, 66);
}

.tab button:hover {
  background-color: rgb(191, 147, 89);
  color: rgb(144, 58, 32);
  border: 6px solid brown;
  border-radius: 10% / 8px;
}

.tab button:active {
  background-color: rgb(153, 73, 51);
  color: rgb(70, 21, 6);
  border: 4px solid brown;
  border-radius: 10% / 8px;
}

.tabcontent {
  display: none;
  padding: 6px 12px;
  border-top: none;
}

.show {
  display: block;
}
<div id="wrapper">
  <div class="tab">
    <button class="tablinks defaultOpen" data-targettab="profile">Profile</button>
    <button class="tablinks" data-targettab="ref">Ref Sheet</button>
  </div>

  <div id="main">
    <div id="content">
      <div id="profile" class="tabcontent">
        <div id="profileimage"></div>
        <div class="tab2" id="buttons2">
          <button class="tablinks defaultOpen" data-targettab="about">About</button>
          <button class="tablinks" data-targettab="extra">Extra</button>
        </div>
        <div id="about" class="tabcontent">hello</div>
        <div id="extra" class="tabcontent">Extra</div>
      </div>
      <div id="ref" class="tabcontent">
        <div id="references" class="flex-container">
          <div class="box">
            <img src="https://t3.ftcdn/jpg/03/45/05/92/360_F_345059232_CPieT8RIWOUk4JqBkkWkIETYAkmz2b75.jpg">
          </div>
          <div class="box">
            <img src="https://t3.ftcdn/jpg/03/45/05/92/360_F_345059232_CPieT8RIWOUk4JqBkkWkIETYAkmz2b75.jpg">
          </div>
          <div class="box">
            <img src="https://t3.ftcdn/jpg/03/45/05/92/360_F_345059232_CPieT8RIWOUk4JqBkkWkIETYAkmz2b75.jpg">
          </div>
          <div class="box">
            <img src="https://t3.ftcdn/jpg/03/45/05/92/360_F_345059232_CPieT8RIWOUk4JqBkkWkIETYAkmz2b75.jpg">
          </div>
          <div class="box">
            <img src="https://t3.ftcdn/jpg/03/45/05/92/360_F_345059232_CPieT8RIWOUk4JqBkkWkIETYAkmz2b75.jpg">
          </div>
          <div class="box">
            <img src="https://t3.ftcdn/jpg/03/45/05/92/360_F_345059232_CPieT8RIWOUk4JqBkkWkIETYAkmz2b75.jpg">
          </div>
        </div>
      </div>
    </div>
  </div>
</div>

本文标签: