0

I am making a webpage for a soccer roster. I am doing a collapse/expand so when you click on the player picture it will expand information/stats. When I click on the player it will expand all of the players and I just want it to expand just the one player you click. If anyone could help me figure out the CSS code so when you click a single player it will expand their information rather than all of the players.

This is my code:

body {
  font-family: "Open Sans", Arial;
}

main {
  background: #EEE;
  width: 300px;
  margin: 20px auto;
  padding: 10px 0;
}

h2 {
  text-align: center;
}

h3 {
  text-align: center;
}

p {
  text-align: center;
  font-size: 13px;
}

input {
  display: none;
  visibility: collapse;
}

label {
  display: block;
  padding: 0.5em;
  text-align: center;
}

label:hover {
  cursor: grabbing;
  color: #000;
}

.expand {
  height: 0px;
  overflow: hidden;
  color: #FFF;
}

section {
  padding: 0 20px;
}

#toggle:checked~.expand {
  height: 300px;
}

#toggle:checked~label::before {
  content: "-";
}

#toggle2:checked~.expand {
  height: 300px;
}

#toggle2:checked~label::before {
  content: "-";
}
<input id="toggle" type="checkbox">
<label for="toggle"><img src="https://media-public.fcbarcelona.com/20157/0/document_thumbnail/20197/148/55/202/46806932/1.0-1/46806932.jpg?t=1495555185000" width="200" height="250" alt=""/></label>

<div class="expand">
  <section>
    <h3>Lionel Messi</h3>
    <p></p>
  </section>
</div>

<input id="toggle2" type="checkbox">
<label for="toggle2"><img src="https://upload.wikimedia.org/wikipedia/commons/3/39/DK-Beshiktash_%281%29.jpg" width="200" height="250" alt=""/></label>
<div class="expand">
  <section>
    <h3>Other content</h3>
    <p></p>
  </section>
</div>
Rob
  • 14,107
  • 28
  • 46
  • 64
king_coney
  • 93
  • 2
  • 9
  • Did you take a look at the HTML `
    ` tag? https://www.w3schools.com/tags/tag_summary.asp Maybe it can suit your purposes
    – flen Dec 02 '17 at 19:59
  • Possible duplicate of [Pure CSS collapse/expand div](https://stackoverflow.com/questions/15095933/pure-css-collapse-expand-div) , see also https://stackoverflow.com/questions/26121131/expand-and-collapse-with-css – flen Dec 02 '17 at 20:19
  • Please see my edited answer, I fixed your code. If you still have questions feel free to ask them. If I solved your problem, you should check my answer to mark this question as "solved" – flen Dec 03 '17 at 01:55
  • ["Can someone help me?" is not an actual question](https://meta.stackoverflow.com/a/284237/162698) You are required to write your own code and show us what you tried. We can help you with that but SO is not a code writing service. – Rob Dec 04 '17 at 03:18

2 Answers2

1

Could <details> work for you?

#player {
  border: 1px solid black;
  font-size: 150%;
  max-width: 100px;
  height: 200px;
}
<div id="player">
PICTURE OF THE PLAYER
</div>
<details>
A very cool player!
</details>

For information on how to style details, you can have a look at MDN.

From what I read in your question, I don't think it's possible to do a collapse/expand with only CSS. I think you will need JavaScript to element.classList.toggle() the classes. Update: You're right, there are CSS only solutions to collapse/expand, you can check the StackOverflow answers I commented on your question and also this instructive post: http://www.cssportal.com/css3-preview/showing-and-hiding-content-with-pure-css3.php . Still, unless otherwise needed, it really seems to be easier to also use JavaScript.


Re-reading your question, I found what's wrong in it. You're using the wrong CSS selectors. When you use input~div you're selecting all divs that are preceded by an input. That means that when you click on #toggle, you are also selecting the div of #toggle2 (and also of toggle3, toggle4, etc.), because it is also preceded in the HTML by #toggle1.

You should use the input+div selector instead. This way only the divs that are placed immediately after an input will be selected. So #toggle:checked+div.expand will select only the div with class "expand" that is immediately preceded by #toggle (all the next divs will not be selected any more).

But for this to work, I had to put the divs immediately after the inputs in your HTML. Otherwise, they would not be selected. This does not make any difference since your <label> tags already reference (with for="...) your inputs' names.

I corrected your code and made some comments:

body {
  font-family: "Open Sans", Arial;
}

main {
  background: #EEE;
  width: 300px;
  margin: 20px auto;
  padding: 10px 0;
}

h2 {
  text-align: center;
}

h3 {
  text-align: center;
}

p {
  text-align: center;
  font-size: 13px;
}

input {
  display: none;
  visibility: collapse;
}

label {
  display: block;
  padding: 0.5em;
  text-align: center;
}

label:hover {
  //cursor: grabbing;
  /*doesn't it make more sense to use 'pointer'?*/
  cursor: pointer;
  color: #000;/*what's the point of this rule?*/
}

.expand {
  height: 0px;
  overflow: hidden;
  //color: #FFF;
  /*this 'color' rule makes your text white.
  In a white background-color, you can't see
  the text, because background and text are white*/
}

section {
  padding: 0 20px;
}

/*old: #toggle:checked~.expand {
I changed all "~" for "+" below:*/
#toggle:checked+.expand {
  height: 300px;
}

#toggle:checked+label::before {
  content: "-";/*this here adds an "-" before
  the element. What's the point of this? I think you should get rid of these ::before selectors*/
}

#toggle2:checked+.expand {
  height: 300px;
}

#toggle2:checked+label::before {
  content: "-";
}
<!-- old: <input id="toggle" type="checkbox"> , I moved it below -->
<label for="toggle"><img src="https://media-public.fcbarcelona.com/20157/0/document_thumbnail/20197/148/55/202/46806932/1.0-1/46806932.jpg?t=1495555185000" width="200" height="250" alt=""/></label>

<input id="toggle" type="checkbox">

<div class="expand">
  <section>
    <h3>Lionel Messi</h3>
    <p>A brief description of whatever</p>
  </section>
</div>

<!-- old: <input id="toggle2" type="checkbox"> , I moved it below -->
<label for="toggle2"><img src="https://upload.wikimedia.org/wikipedia/commons/3/39/DK-Beshiktash_%281%29.jpg" width="200" height="250" alt=""/></label>

<input id="toggle2" type="checkbox">

<div class="expand">
  <section>
    <h3>Other content</h3>
    <p>Another paragraph</p>
  </section>
</div>

An even better code would be:

.expand {
  /*erase the 'height' and 'overflow' rules*/
  display: none;
}

#toggle:checked+.expand {
  display: initial;
}

Update: flexbox 4x4

Bear in mind that the client's screen size may vary (think of mobile devices too) and so may the browser window. A flexbox will make your content wrap if it reaches the end of the screen. But if you want a fixed 4x4 format, you can place 4 flexboxes on top of each other with the CSS set to flex-wrap: nowrap;, or even better, use a CSS grid for that. There are many tutorials on how to do it, but it will take you some time to get the hang of it.

Here's my suggestion for a wrapable flexbox:
(when running this code snippet, click on "Full page" and resize the browser window to see what I'm talking about)

.flex-container {
  display:flex;
  flex-wrap: wrap;
  background-color: #ccc;
  justify-content: space-around;  
}

.flex-container>div {
  background-color: #333;
  color: white;
  width: 200px;
  height: 200px;
  margin: 20px;
  text-align: center;
}
<div class="flex-container">
  <div>player1</div>
  <div>player2</div>
  <div>player3</div>
  <div>player4</div>
  <div>player5</div>
  <div>player6</div>
  <div>player7</div>
  <div>player8</div>
  <div>player1</div>
  <div>player2</div>
  <div>player3</div>
  <div>player4</div>
  <div>player5</div>
  <div>player6</div>
  <div>player7</div>
  <div>player8</div>   
</div> 

I'm sorry if the answer is too verbose, I tried to be very clear since you told me you're beginning to code. Please tell me if there's anything unclear.

flen
  • 1,631
  • 1
  • 18
  • 42
  • So the above code did work. The pictures just are on top of each other vertically with no spacing. So I will have to figure the CSS part out for that. Is there a way to float the images left, center, and right? So I could have 4-5 players in one row? – king_coney Dec 02 '17 at 20:22
  • Sure! You can use CSS `grid` or maybe a `flexbox`. But what is the "above code" you mentioned? The one in my answer or the one in your question? – flen Dec 02 '17 at 20:25
  • The
    did work. I was able to show information for the one player that I clicked on. When I want to space them out in CSS do I need to use the #player?
    – king_coney Dec 02 '17 at 20:28
  • Yes, but the `#player` is only a CSS selector to the element with `id="player"`. You could have a `class="player"` (`.player`) or just about any other selector. Sorry if you already know this, but as you are new to the site I don't know how much experience you have with front-end web development. If you want to space out the player's `` (in my example, `
    `) from the `
    `, you could set `#player {margin-bottom: 20px;}`, for example
    – flen Dec 02 '17 at 20:36
  • Flen, I am a beginner in coding. I know basically nothing about JS. This is all very new to me. I have never used this website so this is my first time. I just figured the HTML/CSS expand/collapse would be the easiest way since this project is due this Thursday. And getting these players is my last major task to the page. – king_coney Dec 02 '17 at 20:40
  • Fear not! I myself am a self-taught programmer, and StackOverflow is a great site to learn, I learn a lot here. Just be a little careful that if you post a question that has already been asked, you're likely to get downvoted and have no answers. w3schools.com has some OK free tutorials for beginners (a little outdated and not the best info, IMO), they are easy to catch on – flen Dec 02 '17 at 20:44
  • Just a heads-up: I used an `id` because "ids" are meant to identify only *one* element in your HTML. In my example, I only had *one* player's photo. But since you want to put many players, you should use a `class` instead. Classes are a way to select multiple elements. Therefore: instead of having a `
    ` (or an ``. And the way to select a class in CSS is: `.player {margin-bottom: 15px; /*or whatever other rule*/}`, instead of `#player {margin-bo...` (`#` selects an `id`, `.` selects a class)
    – flen Dec 02 '17 at 21:15
  • Maybe this tutorial can come in hand, you can simply copy and paste for the most part: https://www.w3schools.com/howto/howto_css_image_overlay.asp . There are other interesting how-tos here also https://www.w3schools.com/howto/default.asp – flen Dec 02 '17 at 22:01
  • I will check that tutorial out and see what I can do. Thank you – king_coney Dec 02 '17 at 22:24
  • Flen thank you. your corrected code you fixed and explain to me makes way more sense to me. And it looks way cleaner this way. Thank you very much. – king_coney Dec 03 '17 at 21:03
  • The code works great. The only thing i am having trouble with is placing images in a 4x4 format. I tried to do a 4x4 stack image because there is 16 players. I tried a
    – king_coney Dec 03 '17 at 21:21
  • Glad I could help! If it solved the question, please mark it afterwards as solved https://meta.stackexchange.com/questions/5234/how-does-accepting-an-answer-work , so that the question doesn't linger on open forever. As regards the 4x4 format, here's a tutorial: https://www.w3schools.com/css/css3_flexbox.asp I'll update my answer with it – flen Dec 04 '17 at 02:42
  • Your answer is the poster boy for why off topic questions like this one should not be answered at all. https://stackoverflow.com/help/how-to-answer – Rob Dec 04 '17 at 03:19
  • @Rob, I guess you're right, but I wanted to help someone that's starting now, I know how daunting it is to begin web development with noone to talk to. But what's your suggestion, should I stop replying? – flen Dec 04 '17 at 03:29
  • @king_coney if all this is too hard for you to deliver on Thursday, remember you can use an open-source CMS like wordpress.org (many tutorials on youtube) or other services around the web (google it), like this one https://flexbox.webflow.com/#collectiongrid – flen Dec 04 '17 at 03:36
  • Yes. As stated in the link I gave: "Answer well-asked questions. Not all questions can or should be answered here. Save yourself some frustration and avoid trying to answer questions which..." – Rob Dec 04 '17 at 03:56
  • Thank you Flen. I believe I clicked this answered my questions. Rob, I am new to this website and i searched for collapse/expand and couldn't find it. That is why I asked the question. – king_coney Dec 04 '17 at 17:34
0

Something like this?

var checkboxes = document.querySelectorAll('input[type=checkbox]'); 
for (var i = 0; i < checkboxes.length; i++) {
console.log('iran');
  checkboxes[i].addEventListener("change", checkboxFunction);
}

//document.querySelector(".expand > section > h3").innerHTML = "Nothin"
function checkboxFunction(){
  switch (this.id) {
    case 'toggle1':
          document.getElementById("toggle2").checked = false;
          document.querySelector(".expand > section > h3").innerHTML = "Foo"
          document.querySelector(".expand > section > p").innerHTML = "Red"
          break;
    case 'toggle2':
          document.getElementById("toggle1").checked = false;
          document.querySelector(".expand > section > h3").innerHTML = "Bar"
          document.querySelector(".expand > section > p").innerHTML = "Blue"
          break;
  }
}
<input id="toggle1" type="checkbox">
<label for="toggle1">
  <img src="https://media-public.fcbarcelona.com/20157/0/document_thumbnail/20197/148/55/202/46806932/1.0-1/46806932.jpg?t=1495555185000" width="40" height="45" alt=""/>
</label>


<input id="toggle2" type="checkbox">
<label for="toggle2">
  <img src="https://upload.wikimedia.org/wikipedia/commons/3/39/DK-Beshiktash_%281%29.jpg" width="40" height="45" alt=""/>
</label>

<div class="expand">
  <section>
    <h3>Other content</h3>
    <p></p>
  </section>
</div>
Ronnie Royston
  • 13,836
  • 5
  • 66
  • 83