WDD12 - JavaScript: showing and hiding content
- I can write a function that changes an element's display property between none and block.
- I can use an if statement to check an element's current state before deciding what to change it to.
- I can trigger a show/hide function from an event such as onclick or onmouseover.
- I can write a function that hides an element by setting its display to none.
- I can write a toggle function that shows a hidden element and hides a shown one, using the same button.
- I can explain why an element should usually start with display: none set explicitly, rather than left unset.
WDD12 combines WDD11's events and functions with WDD7's display property.
Key vocabulary
Showing and hiding with display: none and display: block
JavaScript can change any CSS property, including display
WDD7 introduced display: none as the value that removes an element from the page entirely. WDD11 introduced writing functions and calling them from events. This lesson combines both: a JavaScript function can read or change any CSS property of an element via element.style.propertyName, including display. Setting element.style.display = 'none'; hides the element; setting element.style.display = 'block'; shows it again as a normal block-level element.
function hideAnswer() {
document.getElementById('answer').style.display = 'none';
}
function showAnswer() {
document.getElementById('answer').style.display = 'block';
}
Toggling: one function, two states
Two separate functions, one to show and one to hide, work but need two separate buttons. A more useful pattern is a single toggle function, attached to one button or link, that checks the element's current display value using an if statement and switches to the opposite state. This needs a condition: if the element is currently hidden, show it; otherwise, hide it.
function toggleAnswer() {
var answer = document.getElementById('answer');
if (answer.style.display === 'none') {
answer.style.display = 'block';
} else {
answer.style.display = 'none';
}
}
Why the starting state matters
An element that has no inline style attribute and no matching CSS rule setting display does not start with style.display equal to 'block' or 'none' - it starts as an empty string, because nothing has been set on the element directly yet. A toggle function's if statement is comparing against a specific value, usually 'none', so it is good practice to give the element an explicit starting state - typically style="display: none;" written directly in the HTML - so the very first click behaves exactly as expected, rather than relying on how the empty string happens to compare.
if (el.style.display === 'none') { ... }
Worked examples
<button onclick="hideBox()">Hide</button>
<button onclick="showBox()">Show</button>
<div id="box" style="display: block;">Some content</div>
<script>
function hideBox() {
document.getElementById('box').style.display = 'none';
}
function showBox() {
document.getElementById('box').style.display = 'block';
}
</script>
<button onclick="toggleAnswer()">Show/hide answer</button>
<p id="answer" style="display: none;">42</p>
<script>
function toggleAnswer() {
var answer = document.getElementById('answer');
if (answer.style.display === 'none') {
answer.style.display = 'block';
} else {
answer.style.display = 'none';
}
}
</script>
style="display: none;", so its state is known before any click.<div onmouseover="toggleFaq()">
<p>What are Higher Computing Science's units?</p>
</div>
<p id="faq-answer" style="display: none;">CS, SDD, DDD and WDD.</p>
A paragraph starts with style="display: none;" already set in the HTML. A pupil's toggle function checks if (el.style.display === 'block') instead of checking for 'none'. What happens the very first time the button is clicked?
The element's style.display is currently 'none', not 'block', so the if condition is false.
The else branch runs instead - whatever that branch does happens, which is very likely not the intended "show it" behaviour on this first click.
The check needs to compare against 'none' (the paragraph's actual starting state), not 'block', for the first click to correctly show it.
Practical: toggle function, WebStorm
Build this from scratch - no starter file this time.
- In WebStorm, create a new HTML file called
toggle.html. - Add a button and a paragraph with an id, and give the paragraph
style="display: none;"directly in the HTML. - Write a toggle function using an if statement that checks the paragraph's current display value and switches it.
- Attach the function to the button's onclick attribute.
- Save, open in a browser, and click the button repeatedly to check it shows and hides the paragraph correctly every time, not just once.
<button onclick="toggleParagraph()">Show/hide</button>
<p id="content" style="display: none;">Here is the hidden content.</p>
<script>
function toggleParagraph() {
var el = document.getElementById('content');
if (el.style.display === 'none') {
el.style.display = 'block';
} else {
el.style.display = 'none';
}
}
</script>
Compare your own file against this rather than copying it - the key things to check are the explicit starting display: none in the HTML, and the if/else pair correctly switching both ways.
- Assuming an element's style.display starts as 'block' or 'none' automatically. With no inline style or matching rule set yet, it is actually an empty string - give the element an explicit starting display value in the HTML so the first click behaves correctly.
- Writing only an if with no else. Without an else branch, the function can only ever do one of the two things (usually only show, never hide, or vice versa) - a genuine toggle needs both branches.
- Comparing against the wrong value in the if statement. The condition should check for whatever the element's actual starting state is (usually 'none') - checking for 'block' instead reverses the intended first-click behaviour.
- Forgetting the quotes around 'none' and 'block'. These are text (string) values being compared and assigned, not variable names - missing quotes causes a JavaScript error.
A toggle function needs exactly three things: a reference to the element (document.getElementById), an if/else that checks its current display value, and two assignments that set the opposite value in each branch. If a question shows a "broken toggle," check first whether the else branch is missing, and second whether the element has an explicit starting display value in its HTML.
Task Set A - Core questions
function toggleAnswer() {
var answer = document.getElementById('answer');
if (answer.style.display === 'none') {
answer.style.display = 'block';
}
}
function toggleAnswer() {
var answer = document.getElementById('answer');
if (answer.style.display === 'none') {
answer.style.display = 'block';
} else {
answer.style.display = 'none';
}
}
The if statement has no else branch, so it can only ever set display to 'block' - there is no code anywhere that sets it back to 'none'. Adding the else branch makes it a genuine toggle.
Task Set B - Extension
- In WebStorm, create a new HTML file called
faq.html. - Add three question/answer pairs, each answer a paragraph with its own unique id, starting hidden with style="display: none;".
- Write a separate toggle function for each answer (or one function that takes the id as a parameter, if you are confident with that).
- Attach each question's onclick to its own toggle function.
- Save, open in a browser, and check each question shows and hides only its own answer, independently of the other two.
<p onclick="toggleAnswer1()">Question 1</p>
<p id="a1" style="display: none;">Answer 1</p>
<p onclick="toggleAnswer2()">Question 2</p>
<p id="a2" style="display: none;">Answer 2</p>
<script>
function toggleAnswer1() {
var el = document.getElementById('a1');
if (el.style.display === 'none') { el.style.display = 'block'; }
else { el.style.display = 'none'; }
}
function toggleAnswer2() {
var el = document.getElementById('a2');
if (el.style.display === 'none') { el.style.display = 'block'; }
else { el.style.display = 'none'; }
}
</script>
Compare your own file against this rather than copying it - each answer needs its own unique id and its own toggle logic, so that opening one question never affects another.
File this in OneNote under:
Higher Computing Science > Web Design & Development > WDD12
Timing: content is scoped for a single period but this lesson lands on a double (Mon 7 Dec 2026, per WDD.md §2a/§4 table) - the same "extra time" pattern as WDD6, WDD8 and WDD9. Core pace through Task Set A: 6 min warm up, 12 min show/hide + toggle notes + Examples 1-2, 10 min starting-state notes + context box + Example 3, remaining time on Task Set A. Use the spare second period for the full WebStorm practical in class, Task Set B, and the B3 multi-FAQ extension, which is genuinely useful extra practice rather than filler.
Scope control: if statements are introduced here only as far as needed for a two-branch toggle - no else if, no logical operators (&&, ||), and no loops, matching the WDD scope note that excludes loops entirely. Parameter-based toggle functions (one function reused for multiple elements) are extension-only (B3's optional route), not core content, since SDD's own parameter-passing lesson (SDD8) is the primary place this is taught in depth.
The empty-string starting state is the highest-value gotcha in this lesson, matching the role margin collapse played in WDD8 and percentage height in WDD9 - it is the one behaviour most likely to produce a genuinely confusing bug for a pupil rather than an obviously wrong-looking one. A6/A7/context box and Now-You-Try all test it from different angles.
Practical built from scratch (no starter file), continuing the alternation from WDD11.