{"id":466,"date":"2026-01-06T03:30:41","date_gmt":"2026-01-06T03:30:41","guid":{"rendered":"https:\/\/i-cte.org\/robot\/?p=466"},"modified":"2026-01-06T15:14:54","modified_gmt":"2026-01-06T15:14:54","slug":"ielts-listening-section-3","status":"publish","type":"post","link":"https:\/\/i-cte.org\/robot\/ielts-listening-section-3\/","title":{"rendered":"IELTs &#8211; Listening &#8211; Section 3"},"content":{"rendered":"\n<div id=\"icte-listening-s3\">\n\n  <!-- Top green menu bar -->\n  <div class=\"icte-menu\">\n<a href=\"https:\/\/i-cte.org\/robot\/ielts-listening-overview\/\">Overview<\/a>\n      <a href=\"https:\/\/i-cte.org\/robot\/ielts-listening-section-1\/\">Section 1<\/a>\n      <a href=\"https:\/\/i-cte.org\/robot\/ielts-listening-section-2\/\">Section 2<\/a>\n      <a href=\"https:\/\/i-cte.org\/robot\/ielts-listening-section-3\/\">Section 3<\/a>\n      <a href=\"https:\/\/i-cte.org\/robot\/ielts-listening-section-4\/\">Section 4<\/a>\n      <a href=\"https:\/\/i-cte.org\/robot\/ielts-reading-overview\/\">Reading<\/a>\n      <a href=\"https:\/\/i-cte.org\/robot\/ielts-speaking\/\">Speaking<\/a>\n      <a href=\"https:\/\/i-cte.org\/robot\/ielts-writing-overview\/\">Writing<\/a>\n  <\/div>\n\n  <section class=\"icte-ielts\" aria-label=\"IELTS Listening Section 3 - Library Paper Planning\">\n    <header class=\"icte-ielts__intro\">\n      <h2 class=\"icte-ielts__title\">IELTS Listening \u2013 Section 3 (Questions 21\u201330): Library Paper Planning<\/h2>\n      <p class=\"icte-ielts__sub\">\n        Questions <strong>21\u201323<\/strong>: Choose the correct letter <strong>A, B or C<\/strong>.<br>\n        Questions <strong>24\u201330<\/strong>: Complete the notes. Write <strong>ONE WORD ONLY<\/strong>.\n      <\/p>\n    <\/header>\n\n    <!-- Transcript (hidden by default) -->\n    <section class=\"icte-ielts__panel\" aria-label=\"Transcript\">\n      <div class=\"icte-ielts__panelHead\">\n        <h3 class=\"icte-ielts__h3\">Transcript (for practice)<\/h3>\n        <div class=\"icte-ielts__headRight\">\n          <button class=\"icte-btn icte-btn--dark\" type=\"button\" data-action=\"toggle-transcript\">Show Transcript<\/button>\n          <span class=\"icte-loader\" data-el=\"synthesis-loader\" aria-hidden=\"true\"><\/span>\n        <\/div>\n      <\/div>\n\n      <div class=\"icte-ielts__reading\" data-el=\"transcript-area\" role=\"region\" aria-label=\"Transcript text\" style=\"display:none;\"><\/div>\n\n      <div class=\"icte-ielts__btnRow icte-ielts__btnRow--tight\">\n        <button class=\"icte-btn icte-btn--info\" type=\"button\" data-action=\"play-conversation\">\ud83d\udd0a Listen to the Conversation<\/button>\n        <button class=\"icte-btn icte-btn--danger\" type=\"button\" data-action=\"stop-audio\">\u23f9 Stop Audio<\/button>\n        <a class=\"icte-link\" href=\"#icte-questions\">Jump to questions \u2193<\/a>\n      <\/div>\n    <\/section>\n\n    <!-- Controls -->\n    <section class=\"icte-ielts__panel\" aria-label=\"Controls\">\n      <div class=\"icte-ielts__row\" style=\"align-items:flex-start;\">\n        <div class=\"icte-ielts__control\" style=\"flex:1; min-width:240px;\">\n          <label><strong>Trudie Voice<\/strong><\/label>\n          <select data-el=\"voice-trudie\" aria-label=\"Select Trudie Voice\">\n            <option value=\"\">Loading voices&#8230;<\/option>\n          <\/select>\n        <\/div>\n\n        <div class=\"icte-ielts__control\" style=\"flex:1; min-width:240px;\">\n          <label><strong>Stewart Voice<\/strong><\/label>\n          <select data-el=\"voice-stewart\" aria-label=\"Select Stewart Voice\">\n            <option value=\"\">Loading voices&#8230;<\/option>\n          <\/select>\n        <\/div>\n\n        <div class=\"icte-ielts__score\" data-el=\"scoreBox\" aria-live=\"polite\"><\/div>\n      <\/div>\n\n      <div class=\"icte-ielts__btnGrid\" aria-label=\"Action buttons\">\n        <button class=\"icte-btn icte-btn--info\" type=\"button\" data-action=\"play-instructions\">\ud83d\udd0a Read Instructions<\/button>\n        <button class=\"icte-btn icte-btn--info\" type=\"button\" data-action=\"read-questions\">\ud83d\udd0a Read Questions<\/button>\n        <button class=\"icte-btn icte-btn--primary\" type=\"button\" data-action=\"check\">Check Answers<\/button>\n        <button class=\"icte-btn icte-btn--dark\" type=\"button\" data-action=\"show\">\ud83d\udc40 Show Answers<\/button>\n        <button class=\"icte-btn icte-btn--dark\" type=\"button\" data-action=\"summary\">\ud83e\udde0 Summary<\/button>\n        <button class=\"icte-btn icte-btn--dark\" type=\"button\" data-action=\"main-ideas\">\ud83d\udccc Main ideas<\/button>\n        <button class=\"icte-btn icte-btn--ghost\" type=\"button\" data-action=\"reset\">Reset<\/button>\n      <\/div>\n    <\/section>\n\n    <!-- Support -->\n    <section class=\"icte-ielts__panel\" aria-label=\"Learning support\">\n      <div class=\"icte-ielts__panelHead\">\n        <h3 class=\"icte-ielts__h3\">Support<\/h3>\n        <div class=\"icte-ielts__headRight\">\n          <button class=\"icte-btn icte-btn--ghost\" type=\"button\" data-action=\"clear-support\">Clear<\/button>\n        <\/div>\n      <\/div>\n\n      <div class=\"icte-ielts__helper\" data-el=\"helper-area\" role=\"region\" aria-live=\"polite\">\n        Click <strong>Summary<\/strong> or <strong>Main ideas<\/strong>.\n      <\/div>\n    <\/section>\n\n    <!-- Questions -->\n    <section class=\"icte-ielts__panel\" id=\"icte-questions\" aria-label=\"Questions 21 to 30\">\n      <div class=\"icte-ielts__panelHead\">\n        <h3 class=\"icte-ielts__h3\">Section 3 \u2013 Questions 21\u201330<\/h3>\n      <\/div>\n\n      <div class=\"icte-ielts__qArea\">\n\n        <!-- Q21-23 -->\n        <div class=\"icte-q\">\n          <div class=\"icte-q__label\">Questions 21\u201323<\/div>\n          <div style=\"opacity:.9; line-height:1.65;\">Choose the correct letter, <strong>A<\/strong>, <strong>B<\/strong> or <strong>C<\/strong>.<\/div>\n        <\/div>\n\n        <div class=\"icte-q\">\n          <div class=\"icte-q__label\">Paper on Public Libraries<\/div>\n          <div class=\"icte-q__label\" style=\"font-weight:900;\">21. What will be the main topic of Trudie and Stewart\u2019s paper?<\/div>\n          <div class=\"icte-q__controls icte-opts\" data-q=\"21\">\n            <label><input type=\"radio\" name=\"q21\" value=\"A\"> A. how public library services are organised in different countries<\/label>\n            <label><input type=\"radio\" name=\"q21\" value=\"B\"> B. how changes in society are reflected in public libraries<\/label>\n            <label><input type=\"radio\" name=\"q21\" value=\"C\"> C. how the funding of public libraries has changed<\/label>\n          <\/div>\n          <div class=\"icte-q__fb\" data-fb=\"21\"><\/div>\n        <\/div>\n\n        <div class=\"icte-q\">\n          <div class=\"icte-q__label\">22. They agree that one disadvantage of free digitalised books is that<\/div>\n          <div class=\"icte-q__controls icte-opts\" data-q=\"22\">\n            <label><input type=\"radio\" name=\"q22\" value=\"A\"> A. they may take a long time to read.<\/label>\n            <label><input type=\"radio\" name=\"q22\" value=\"B\"> B. they can be difficult to read.<\/label>\n            <label><input type=\"radio\" name=\"q22\" value=\"C\"> C. they are generally old.<\/label>\n          <\/div>\n          <div class=\"icte-q__fb\" data-fb=\"22\"><\/div>\n        <\/div>\n\n        <div class=\"icte-q\">\n          <div class=\"icte-q__label\">23. Stewart expects that in the future libraries will<\/div>\n          <div class=\"icte-q__controls icte-opts\" data-q=\"23\">\n            <label><input type=\"radio\" name=\"q23\" value=\"A\"> A. maintain their traditional function.<\/label>\n            <label><input type=\"radio\" name=\"q23\" value=\"B\"> B. become centres for local communities.<\/label>\n            <label><input type=\"radio\" name=\"q23\" value=\"C\"> C. no longer contain any books.<\/label>\n          <\/div>\n          <div class=\"icte-q__fb\" data-fb=\"23\"><\/div>\n        <\/div>\n\n        <!-- Q24-30 notes -->\n        <div class=\"icte-q\">\n          <div class=\"icte-q__label\">Questions 24\u201330<\/div>\n          <div style=\"opacity:.9; line-height:1.65;\">\n            Complete the notes below. Write <strong>ONE WORD ONLY<\/strong> for each answer.\n          <\/div>\n        <\/div>\n\n        <div class=\"icte-q\">\n          <div class=\"icte-q__label\">Study of local library: possible questions<\/div>\n          <div class=\"icte-note\">\n            <div>\u2022 whether it has a <span class=\"blank\">24 <input type=\"text\" data-q=\"24\" placeholder=\"ONE WORD\" \/><\/span> on its own<\/div>\n            <div>\u2022 its policy regarding noise of various kinds<\/div>\n            <div>\u2022 how it\u2019s affected by laws regarding all aspects of <span class=\"blank\">25 <input type=\"text\" data-q=\"25\" placeholder=\"ONE WORD\" \/><\/span><\/div>\n            <div>\u2022 how the design needs to take the <span class=\"blank\">26 <input type=\"text\" data-q=\"26\" placeholder=\"ONE WORD\" \/><\/span> of customers into account<\/div>\n            <div>\u2022 what <span class=\"blank\">27 <input type=\"text\" data-q=\"27\" placeholder=\"ONE WORD\" \/><\/span> is required in case of accidents<\/div>\n            <div>\u2022 why a famous person\u2019s <span class=\"blank\">28 <input type=\"text\" data-q=\"28\" placeholder=\"ONE WORD\" \/><\/span> is located in the library<\/div>\n            <div>\u2022 whether it has a <span class=\"blank\">29 <input type=\"text\" data-q=\"29\" placeholder=\"ONE WORD\" \/><\/span> of local organisations<\/div>\n            <div>\u2022 how it\u2019s different from a library in a <span class=\"blank\">30 <input type=\"text\" data-q=\"30\" placeholder=\"ONE WORD\" \/><\/span><\/div>\n          <\/div>\n\n          <div class=\"icte-q__fb\" data-fb=\"24\"><\/div>\n          <div class=\"icte-q__fb\" data-fb=\"25\"><\/div>\n          <div class=\"icte-q__fb\" data-fb=\"26\"><\/div>\n          <div class=\"icte-q__fb\" data-fb=\"27\"><\/div>\n          <div class=\"icte-q__fb\" data-fb=\"28\"><\/div>\n          <div class=\"icte-q__fb\" data-fb=\"29\"><\/div>\n          <div class=\"icte-q__fb\" data-fb=\"30\"><\/div>\n        <\/div>\n\n      <\/div>\n    <\/section>\n\n    <style>\n      \/* Menu *\/\n      #icte-listening-s3 .icte-menu{\n        width:100%; max-width:100%; box-sizing:border-box;\n        display:flex; flex-wrap:wrap; gap:.5rem; justify-content:center; align-items:center;\n        padding:.75rem .9rem; margin:0 0 1rem 0;\n        background:#16a34a; border-radius:14px; box-shadow:0 2px 8px rgba(0,0,0,.10);\n      }\n      #icte-listening-s3 .icte-menu a{\n        display:inline-block; text-decoration:none; font-weight:900; font-size:.95rem; color:#fff;\n        padding:.55rem .85rem; border-radius:999px; border:1px solid rgba(255,255,255,.35);\n        background:rgba(255,255,255,.12);\n      }\n      #icte-listening-s3 .icte-menu a.is-current{ background:#fff; color:#16a34a; border-color:#fff; }\n      @media (max-width:600px){\n        #icte-listening-s3 .icte-menu{ justify-content:flex-start; }\n        #icte-listening-s3 .icte-menu a{ width:100%; text-align:center; }\n      }\n\n      \/* Shared styling *\/\n      #icte-listening-s3 .icte-ielts{ width:100%; margin:1rem 0; }\n      #icte-listening-s3 .icte-ielts__intro{\n        padding:.9rem 1rem; border:1px solid rgba(0,0,0,.10); border-radius:14px;\n        background:rgba(255,255,255,.7); margin-bottom:1rem;\n      }\n      #icte-listening-s3 .icte-ielts__title{ margin:0 0 .35rem; font-size:1.2rem; font-weight:900; }\n      #icte-listening-s3 .icte-ielts__sub{ margin:0; opacity:.85; }\n\n      #icte-listening-s3 .icte-ielts__panel{\n        border:1px solid rgba(0,0,0,.10); border-radius:14px; background:rgba(255,255,255,.85);\n        overflow:hidden; margin-bottom:1rem;\n      }\n      #icte-listening-s3 .icte-ielts__panelHead{\n        display:flex; align-items:center; justify-content:space-between; gap:.75rem;\n        padding:.85rem 1rem; border-bottom:1px solid rgba(0,0,0,.08); background:rgba(0,0,0,.03);\n      }\n      #icte-listening-s3 .icte-ielts__h3{ margin:0; font-size:1.03rem; font-weight:900; }\n      #icte-listening-s3 .icte-ielts__headRight{ display:flex; gap:.55rem; align-items:center; }\n\n      #icte-listening-s3 .icte-ielts__reading{\n        padding:.95rem 1rem 1.05rem; line-height:1.75; max-height:420px; overflow:auto;\n        white-space:pre-wrap;\n      }\n\n      #icte-listening-s3 .icte-ielts__row{\n        display:flex; justify-content:space-between; gap:.75rem;\n        padding:.85rem 1rem .25rem;\n      }\n      #icte-listening-s3 .icte-ielts__control label{ display:block; margin-bottom:.35rem; }\n      #icte-listening-s3 select{\n        width:100%; max-width:520px; padding:.6rem .7rem; border-radius:12px;\n        border:1px solid rgba(0,0,0,.18); background:#fff; font:inherit;\n      }\n      #icte-listening-s3 .icte-ielts__score{\n        font-weight:900; font-size:.95rem; opacity:.9; white-space:nowrap;\n        margin-top:.25rem;\n      }\n\n      #icte-listening-s3 .icte-ielts__btnRow{\n        padding:.75rem 1rem 1rem; display:flex; gap:.6rem; flex-wrap:wrap; align-items:center;\n      }\n      #icte-listening-s3 .icte-ielts__btnRow--tight{ padding-top:0; }\n      #icte-listening-s3 .icte-ielts__btnGrid{\n        padding:.75rem 1rem 1rem;\n        display:grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap:.6rem;\n      }\n\n      #icte-listening-s3 .icte-link{\n        font-weight:900; text-decoration:none; border:1px solid rgba(0,0,0,.14);\n        border-radius:12px; padding:.55rem .75rem; color:inherit; background:rgba(255,255,255,.6);\n      }\n\n      #icte-listening-s3 .icte-ielts__qArea{ padding:.9rem 1rem 1rem; }\n      #icte-listening-s3 .icte-q{\n        padding:.75rem .8rem; border:1px solid rgba(0,0,0,.10); border-radius:12px;\n        background:rgba(255,255,255,.75); margin:0 0 .75rem;\n      }\n      #icte-listening-s3 .icte-q__label{ font-weight:900; display:block; margin-bottom:.4rem; }\n      #icte-listening-s3 .icte-q__fb{ margin-top:.35rem; font-size:.95rem; font-weight:800; }\n\n      \/* Options *\/\n      #icte-listening-s3 .icte-opts{ display:flex; flex-direction:column; gap:.35rem; }\n      #icte-listening-s3 .icte-opts label{\n        display:flex; gap:.55rem; align-items:flex-start;\n        padding:.25rem .35rem; border-radius:10px;\n      }\n      #icte-listening-s3 .icte-opts input{ margin-top:.25rem; }\n\n      \/* Notes inputs *\/\n      #icte-listening-s3 .icte-note{ line-height:1.7; opacity:.95; }\n      #icte-listening-s3 .blank{\n        display:inline-flex; align-items:center; gap:.4rem;\n        padding:.15rem .35rem; border-radius:10px; border:1px dashed rgba(0,0,0,.25);\n        background:rgba(255,255,255,.6); margin:0 .25rem;\n      }\n      #icte-listening-s3 input[type=\"text\"]{\n        width:170px; max-width:100%;\n        padding:.55rem .65rem; border-radius:12px;\n        border:1px solid rgba(0,0,0,.18); font:inherit;\n      }\n\n      \/* Buttons *\/\n      #icte-listening-s3 .icte-btn{\n        appearance:none; border:1px solid transparent; border-radius:12px;\n        padding:.65rem .85rem; font-weight:900; cursor:pointer; font:inherit;\n      }\n      #icte-listening-s3 .icte-btn--primary{ background:#16a34a; color:#fff; }\n      #icte-listening-s3 .icte-btn--info{ background:#0ea5e9; color:#fff; }\n      #icte-listening-s3 .icte-btn--danger{ background:#dc2626; color:#fff; }\n      #icte-listening-s3 .icte-btn--dark{ background:#334155; color:#fff; }\n      #icte-listening-s3 .icte-btn--ghost{ background:transparent; border-color:rgba(0,0,0,.20); color:inherit; }\n\n      \/* Loader *\/\n      #icte-listening-s3 .icte-loader{\n        width:18px; height:18px; border-radius:999px;\n        border:3px solid rgba(0,0,0,.15); border-top-color:#0ea5e9;\n        display:none; animation: icteSpin 1s linear infinite;\n      }\n      @keyframes icteSpin{ to{ transform: rotate(360deg); } }\n\n      \/* Support *\/\n      #icte-listening-s3 .icte-ielts__helper{\n        padding:.95rem 1rem 1.05rem; line-height:1.7; overflow-wrap:anywhere; word-break:break-word;\n      }\n      #icte-listening-s3 .icte-ielts__helper ul{ margin:.4rem 0 0 1.1rem; }\n      #icte-listening-s3 .icte-ielts__helper li{ margin:.35rem 0; }\n      #icte-listening-s3 .icte-ielts__helper .tag{\n        display:inline-block; padding:.15rem .5rem; border-radius:999px;\n        border:1px solid rgba(0,0,0,.12); background:rgba(255,255,255,.7);\n        font-weight:900; font-size:.85rem; margin-right:.4rem;\n      }\n\n      @media (max-width: 900px){\n        #icte-listening-s3 .icte-ielts__btnGrid{ grid-template-columns: repeat(2, minmax(0, 1fr)); }\n      }\n      @media (max-width: 600px){\n        #icte-listening-s3 .icte-ielts__row{ flex-direction:column; align-items:stretch; }\n        #icte-listening-s3 .icte-ielts__btnGrid{ grid-template-columns: 1fr; }\n        #icte-listening-s3 input[type=\"text\"]{ width:100%; }\n      }\n    <\/style>\n\n    <script>\n      (function(){\n        const root = document.getElementById(\"icte-listening-s3\");\n        if (!root) return;\n\n        \/\/ ===== Conversation lines (NO spoken labels) =====\n        const lines = [\n          { speaker:\"TRUDIE\",  text:\"OK, Stewart. We need to start planning our paper on public libraries. Have you thought of an angle yet?\" },\n          { speaker:\"STEWART\", text:\"Well, there's so much we could look into. How libraries have changed over the centuries, for instance, or how different countries organise them. What do you think?\" },\n          { speaker:\"TRUDIE\",  text:\"Maybe we should concentrate on this country, and try and relate the changes in libraries to external developments, like the fact that far more people can read than a century ago, and that the local population may speak lots of different languages.\" },\n          { speaker:\"STEWART\", text:\"We could include something about changes in the source of funding, too.\" },\n          { speaker:\"TRUDIE\",  text:\"Yes, but remember we're only supposed to write a short paper, so it's probably best if we don't go into funding in any detail.\" },\n          { speaker:\"STEWART\", text:\"Right. Well, shall we just brainstorm a few ideas, to get started?\" },\n          { speaker:\"TRUDIE\",  text:\"OK. We obviously need to look at the impact of new technology, particularly the internet. Now that lots of books have been digitalised, people can access them from their own computers at home.\" },\n          { speaker:\"STEWART\", text:\"And if everyone did that, libraries would be obsolete.\" },\n          { speaker:\"TRUDIE\",  text:\"Yes.\" },\n          { speaker:\"STEWART\", text:\"But the digitalised books that are available online for free are mostly out of copyright, aren't they? And copyright in this country lasts for seventy years after the author dies. So you won't find the latest best-seller or up-to-date information.\" },\n          { speaker:\"TRUDIE\",  text:\"That's an important point. Anyway, I find it hard to concentrate when I'm reading a long text on a screen. I'd much rather read a physical book. And it takes longer to read on a screen.\" },\n          { speaker:\"STEWART\", text:\"Oh, I prefer it. I suppose it's just a personal preference.\" },\n          { speaker:\"TRUDIE\",  text:\"Mm. I expect that libraries will go on evolving in the next few years. Some have already become centres where community activities take place, like local clubs meeting there. I think that'll become even more common.\" },\n          { speaker:\"STEWART\", text:\"I'd like to think so, and that they'll still be serving their traditional function, but I'm not so sure. There are financial implications, after all. What I'm afraid will happen is that books and magazines will all disappear, and there'll just be rows and rows of computers.\" },\n          { speaker:\"TRUDIE\",  text:\"Well, we'll see. I've just had an idea. Why don't we make an in-depth study of our local public library as background to our paper?\" },\n          { speaker:\"STEWART\", text:\"Yes, that'd be interesting, and raise all sorts of issues. Let's make a list of possible things we could ask about, then work out some sort of structure.\" },\n          { speaker:\"STEWART\", text:\"For instance, we could interview some of the staff, and find out whether the library has its own budget, or if that's controlled by the local council.\" },\n          { speaker:\"TRUDIE\",  text:\"And what their policies are. I know they don't allow food, but I'd love to find out what types of noise they ban\u2014there always seems to be a lot of talking, but never music.\" },\n          { speaker:\"STEWART\", text:\"Then there are things like how the library is affected by employment laws. I suppose there are rules about working hours, facilities for staff, and so on.\" },\n          { speaker:\"TRUDIE\",  text:\"Then there are other issues relating to the design of the building and how customers use it. Like what measures does the library take to ensure their safety? And there's the question of the kind of insurance the library needs to have, in case anyone gets injured.\" },\n          { speaker:\"STEWART\", text:\"You know they've got an archive of local newspapers going back years? Next to it they've got the diary of a well-known politician from the late nineteenth century. I wonder why it's there.\" },\n          { speaker:\"TRUDIE\",  text:\"No idea. Let's add it to our list of things to find out.\" },\n          { speaker:\"TRUDIE\",  text:\"You know people might ask in the library about local organisations, like sports clubs? I wonder if they keep a database, or whether they just look online.\" },\n          { speaker:\"STEWART\", text:\"Right. I quite fancy finding out what the differences are between a library that's open to the public and one that's part of a museum, for example\u2014they must be very different.\" }\n        ];\n\n        const transcriptText = lines.map(l => (l.speaker===\"TRUDIE\" ? \"Trudie: \" : \"Stewart: \") + l.text).join(\"\\n\");\n\n        \/\/ ===== Answers =====\n        const answersMCQ = { 21:\"B\", 22:\"C\", 23:\"C\" };\n        const answersWords = {\n          24:[\"budget\"],\n          25:[\"employment\"],\n          26:[\"safety\"],\n          27:[\"insurance\"],\n          28:[\"diary\"],\n          29:[\"database\"],\n          30:[\"museum\"]\n        };\n\n        const $ = (sel) => root.querySelector(sel);\n        const $$ = (sel) => Array.from(root.querySelectorAll(sel));\n\n        function showLoader(show){\n          const el = $('[data-el=\"synthesis-loader\"]');\n          if (el) el.style.display = show ? \"inline-block\" : \"none\";\n        }\n\n        \/\/ ===== Speech synthesis (robust Stop) =====\n        const speechOk = (\"speechSynthesis\" in window);\n        let voicesAll = [];\n        let voiceTrudie = null;\n        let voiceStewart = null;\n\n        let playRunId = 0;\n\n        function stopSpeaking(){\n          if (!speechOk) return;\n          playRunId++;\n          window.speechSynthesis.cancel();\n          showLoader(false);\n        }\n\n        function sayWithVoice(text, voice, opts){\n          const myRun = playRunId;\n          const options = opts || {};\n          return new Promise((resolve) => {\n            if (!speechOk) return resolve();\n\n            const u = new SpeechSynthesisUtterance(String(text || \"\"));\n            u.lang  = options.lang  || (voice && voice.lang) || \"en-US\";\n            u.rate  = (typeof options.rate === \"number\") ? options.rate : 1.0;\n            u.pitch = (typeof options.pitch === \"number\") ? options.pitch : 1.0;\n            if (voice) u.voice = voice;\n\n            let done = false;\n            const finish = () => {\n              if (done) return;\n              done = true;\n              clearInterval(timer);\n              u.onend = null;\n              u.onerror = null;\n              resolve();\n            };\n\n            u.onend = finish;\n            u.onerror = finish;\n\n            const timer = setInterval(() => {\n              if (done) return;\n              if (playRunId !== myRun) return finish();\n              const speaking = window.speechSynthesis.speaking;\n              const pending  = window.speechSynthesis.pending;\n              if (!speaking && !pending) finish();\n            }, 120);\n\n            window.speechSynthesis.speak(u);\n          });\n        }\n\n        function pickDefaults(usable){\n          const a = usable[0] || null;\n          let b = usable.find(v => v.name !== (a && a.name)) || null;\n          if (!b) b = usable[0] || null;\n          voiceTrudie = a;\n          voiceStewart = b;\n        }\n\n        function populateVoiceSelects(){\n          if (!speechOk) return;\n\n          voicesAll = window.speechSynthesis.getVoices() || [];\n          const en = voicesAll.filter(v => (v.lang || \"\").toLowerCase().startsWith(\"en\"));\n          const usable = en.length ? en : voicesAll;\n\n          const selT = $('[data-el=\"voice-trudie\"]');\n          const selS = $('[data-el=\"voice-stewart\"]');\n          if (!selT || !selS) return;\n\n          selT.innerHTML = \"\";\n          selS.innerHTML = \"\";\n\n          usable.forEach((v, idx) => {\n            const o1 = document.createElement(\"option\");\n            o1.value = String(idx);\n            o1.textContent = `${v.name} (${v.lang})`;\n            selT.appendChild(o1);\n\n            const o2 = document.createElement(\"option\");\n            o2.value = String(idx);\n            o2.textContent = `${v.name} (${v.lang})`;\n            selS.appendChild(o2);\n          });\n\n          pickDefaults(usable);\n\n          if (voiceTrudie){\n            const idx = usable.findIndex(v => v.name === voiceTrudie.name && v.lang === voiceTrudie.lang);\n            if (idx >= 0) selT.value = String(idx);\n          }\n          if (voiceStewart){\n            const idx = usable.findIndex(v => v.name === voiceStewart.name && v.lang === voiceStewart.lang);\n            if (idx >= 0) selS.value = String(idx);\n          }\n\n          selT.onchange = () => { voiceTrudie = usable[Number(selT.value)] || usable[0] || null; };\n          selS.onchange = () => { voiceStewart = usable[Number(selS.value)] || usable[0] || null; };\n        }\n\n        function loadVoices(){\n          if (!speechOk) return;\n          const got = window.speechSynthesis.getVoices();\n          if (got && got.length) populateVoiceSelects();\n          else window.speechSynthesis.onvoiceschanged = populateVoiceSelects;\n        }\n\n        \/\/ ===== Transcript =====\n        function renderTranscript(){\n          const area = $('[data-el=\"transcript-area\"]');\n          if (area) area.textContent = transcriptText;\n        }\n\n        function toggleTranscript(){\n          const area = $('[data-el=\"transcript-area\"]');\n          const btn = root.querySelector('[data-action=\"toggle-transcript\"]');\n          if (!area || !btn) return;\n\n          const hidden = area.style.display === \"none\";\n          area.style.display = hidden ? \"block\" : \"none\";\n          btn.textContent = hidden ? \"Hide Transcript\" : \"Show Transcript\";\n          if (hidden) area.scrollIntoView({ behavior: \"smooth\", block: \"start\" });\n        }\n\n        \/\/ ===== Support (Summary + Main Ideas) =====\n        function setHelperContent(nodesBuilder){\n          const area = $('[data-el=\"helper-area\"]');\n          if (!area) return;\n          area.innerHTML = \"\";\n          nodesBuilder(area);\n          area.scrollIntoView({ behavior: \"smooth\", block: \"start\" });\n        }\n\n        function getSummaryText(){\n          return [\n            \"Two students plan a short paper about public libraries, focusing on how social changes in their country have shaped libraries.\",\n            \"They discuss technology and free digitised books, noting that many are out of copyright and therefore generally old.\",\n            \"They disagree about future libraries: one expects libraries may become more computer-based and contain fewer books.\",\n            \"They decide to study their local library and list questions about budget, employment laws, customer safety, insurance, special historical items, a database of local organisations, and comparison with a museum library.\"\n          ].join(\" \");\n        }\n\n        function getMainIdeas(){\n          return [\n            { tag: \"Q21\u201323\", text: \"Choose the option that matches what they agree on (topic, disadvantage of free digital books, Stewart\u2019s view of the future).\" },\n            { tag: \"Digital books\", text: \"Key idea: free online books are often out of copyright \u2192 generally old.\" },\n            { tag: \"Future libraries\", text: \"Stewart worries books\/magazines will disappear and be replaced by computers.\" },\n            { tag: \"Q24\u201330\", text: \"ONE WORD ONLY. Focus on the exact noun: budget, employment, safety, insurance, diary, database, museum.\" }\n          ];\n        }\n\n        async function showSummary(){\n          const s = getSummaryText();\n          setHelperContent((area) => {\n            const p = document.createElement(\"p\");\n            const tag = document.createElement(\"span\");\n            tag.className = \"tag\";\n            tag.textContent = \"Summary\";\n            p.appendChild(tag);\n            p.append(\" \" + s);\n            area.appendChild(p);\n          });\n\n          if (speechOk){\n            stopSpeaking();\n            showLoader(true);\n            await sayWithVoice(\"Summary. \" + s, voiceTrudie || null, { lang:\"en-US\" });\n            showLoader(false);\n          }\n        }\n\n        async function showMainIdeas(){\n          const items = getMainIdeas();\n          setHelperContent((area) => {\n            const p = document.createElement(\"p\");\n            const tag = document.createElement(\"span\");\n            tag.className = \"tag\";\n            tag.textContent = \"Main ideas\";\n            p.appendChild(tag);\n            p.append(\" Tips for answering these questions:\");\n            area.appendChild(p);\n\n            const ul = document.createElement(\"ul\");\n            items.forEach(i => {\n              const li = document.createElement(\"li\");\n              const t = document.createElement(\"span\");\n              t.className = \"tag\";\n              t.textContent = i.tag;\n              li.appendChild(t);\n              li.append(i.text);\n              ul.appendChild(li);\n            });\n            area.appendChild(ul);\n          });\n\n          if (speechOk){\n            stopSpeaking();\n            showLoader(true);\n            const speakText = \"Main ideas. \" + items.map(i => `${i.tag}. ${i.text}`).join(\" \");\n            await sayWithVoice(speakText, voiceTrudie || null, { lang:\"en-US\" });\n            showLoader(false);\n          }\n        }\n\n        function clearSupport(){\n          const area = $('[data-el=\"helper-area\"]');\n          if (area) area.innerHTML = 'Click <strong>Summary<\/strong> or <strong>Main ideas<\/strong>.';\n        }\n\n        \/\/ ===== Audio buttons =====\n        async function playInstructions(){\n          if (!speechOk) return;\n          stopSpeaking();\n          showLoader(true);\n          const msg =\n            \"Listening Section 3. Questions twenty-one to twenty-three: choose the correct letter A, B, or C. \" +\n            \"Questions twenty-four to thirty: complete the notes. Write one word only for each answer.\";\n          await sayWithVoice(msg, voiceTrudie || null, { lang:\"en-US\" });\n          showLoader(false);\n        }\n\n        async function readQuestions(){\n          if (!speechOk) return;\n          stopSpeaking();\n          showLoader(true);\n          const msg =\n            \"Questions twenty-one to twenty-three. Choose A, B, or C. \" +\n            \"Question twenty-one: main topic of the paper. \" +\n            \"Question twenty-two: disadvantage of free digitalised books. \" +\n            \"Question twenty-three: Stewart's expectation about future libraries. \" +\n            \"Questions twenty-four to thirty. Complete the notes: one word only for each answer.\";\n          await sayWithVoice(msg, voiceTrudie || null, { lang:\"en-US\" });\n          showLoader(false);\n        }\n\n        async function playConversation(){\n          if (!speechOk) return;\n\n          stopSpeaking();\n          const myRun = playRunId;\n\n          if (!voiceTrudie || !voiceStewart) populateVoiceSelects();\n          showLoader(true);\n\n          await sayWithVoice(\"Now listen to the conversation.\", voiceTrudie || null, { lang:\"en-US\" });\n          if (playRunId !== myRun) { showLoader(false); return; }\n\n          for (const l of lines){\n            if (playRunId !== myRun) { showLoader(false); return; }\n\n            const v = (l.speaker === \"TRUDIE\") ? (voiceTrudie || null) : (voiceStewart || null);\n\n            \/\/ Light variation for a more natural two-speaker effect\n            const opts = (l.speaker === \"TRUDIE\")\n              ? { lang:\"en-US\", rate:1.00, pitch:1.02 }\n              : { lang:\"en-US\", rate:1.02, pitch:0.98 };\n\n            await sayWithVoice(l.text, v, opts);\n          }\n\n          showLoader(false);\n        }\n\n        \/\/ ===== Checking =====\n        function setScore(msg){\n          const box = $('[data-el=\"scoreBox\"]');\n          if (box) box.textContent = msg || \"\";\n        }\n\n        function setFB(q, msg, color){\n          const fb = root.querySelector(`[data-fb=\"${q}\"]`);\n          if (!fb) return;\n          fb.textContent = msg || \"\";\n          fb.style.color = color || \"#0f172a\";\n        }\n\n        function getRadioAnswer(q){\n          const el = root.querySelector(`input[name=\"q${q}\"]:checked`);\n          return el ? String(el.value || \"\").trim().toUpperCase() : \"\";\n        }\n\n        function normWord(x){\n          return String(x || \"\")\n            .trim()\n            .toLowerCase()\n            .replace(\/[.,!?;:()\"']\/g, \"\")\n            .replace(\/\\s+\/g, \" \");\n        }\n\n        function tokenCount(x){\n          const t = String(x || \"\").trim();\n          if (!t) return 0;\n          return t.split(\/\\s+\/).length;\n        }\n\n        function check(){\n          const total = 10;\n          let correct = 0;\n          let attempted = 0;\n\n          \/\/ clear feedback\n          for (let q=21; q<=30; q++) setFB(q, \"\", \"\");\n\n          \/\/ Q21-23 MCQ\n          [21,22,23].forEach(q => {\n            const user = getRadioAnswer(q);\n            if (!user){\n              setFB(q, \"Please choose A, B, or C.\", \"#8a5a00\");\n              return;\n            }\n            attempted++;\n            if (user === answersMCQ[q]){\n              correct++;\n              setFB(q, `\u2705 Correct (${answersMCQ[q]})`, \"#065f46\");\n            } else {\n              setFB(q, `\u274c Not correct. Correct answer: ${answersMCQ[q]}`, \"#991b1b\");\n            }\n          });\n\n          \/\/ Q24-30 one word\n          [24,25,26,27,28,29,30].forEach(q => {\n            const input = root.querySelector(`input[data-q=\"${q}\"]`);\n            const raw = input ? String(input.value || \"\").trim() : \"\";\n            if (!raw){\n              setFB(q, \"Please write ONE WORD ONLY.\", \"#8a5a00\");\n              return;\n            }\n            attempted++;\n\n            if (tokenCount(raw) > 1){\n              setFB(q, `\u26a0\ufe0f ONE WORD ONLY. Correct answer: ${answersWords[q][0]}`, \"#8a5a00\");\n              return;\n            }\n\n            const user = normWord(raw);\n            const ok = (answersWords[q] || []).some(a => normWord(a) === user);\n\n            if (ok){\n              correct++;\n              setFB(q, `\u2705 Correct (${answersWords[q][0]})`, \"#065f46\");\n            } else {\n              setFB(q, `\u274c Not correct. Correct answer: ${answersWords[q][0]}`, \"#991b1b\");\n            }\n          });\n\n          setScore(`Score: ${correct}\/${total} (attempted: ${attempted}\/${total})`);\n\n          if (speechOk){\n            showLoader(true);\n            sayWithVoice(`Your score is ${correct} out of ${total}.`, voiceTrudie || null, { lang:\"en-US\" })\n              .then(() => showLoader(false));\n          }\n        }\n\n        function showAll(){\n          [21,22,23].forEach(q => setFB(q, `Correct answer: ${answersMCQ[q]}`, \"#0f172a\"));\n          [24,25,26,27,28,29,30].forEach(q => setFB(q, `Correct answer: ${answersWords[q][0]}`, \"#0f172a\"));\n          setScore(\"Correct answers are shown.\");\n        }\n\n        function reset(){\n          \/\/ radios\n          [21,22,23].forEach(q => {\n            $$(`input[name=\"q${q}\"]`).forEach(r => r.checked = false);\n            setFB(q, \"\", \"\");\n          });\n\n          \/\/ inputs\n          [24,25,26,27,28,29,30].forEach(q => {\n            const inp = root.querySelector(`input[data-q=\"${q}\"]`);\n            if (inp) inp.value = \"\";\n            setFB(q, \"\", \"\");\n          });\n\n          setScore(\"\");\n          clearSupport();\n          stopSpeaking();\n        }\n\n        function markCurrentMenu(){\n          const here = (location.href || \"\").replace(\/\\\/$\/, \"\");\n          root.querySelectorAll(\".icte-menu a\").forEach(a => {\n            const href = (a.href || \"\").replace(\/\\\/$\/, \"\");\n            if (href && (here === href || here.startsWith(href + \"\/\"))) a.classList.add(\"is-current\");\n          });\n        }\n\n        function wire(){\n          const bind = (action, fn) => {\n            const el = root.querySelector(`[data-action=\"${action}\"]`);\n            if (el) el.addEventListener(\"click\", fn);\n          };\n\n          bind(\"toggle-transcript\", toggleTranscript);\n          bind(\"play-conversation\", playConversation);\n          bind(\"stop-audio\", stopSpeaking);\n\n          bind(\"play-instructions\", playInstructions);\n          bind(\"read-questions\", readQuestions);\n\n          bind(\"check\", check);\n          bind(\"show\", showAll);\n          bind(\"reset\", reset);\n\n          bind(\"summary\", showSummary);\n          bind(\"main-ideas\", showMainIdeas);\n          bind(\"clear-support\", clearSupport);\n        }\n\n        function init(){\n          renderTranscript();\n          loadVoices();\n          wire();\n          markCurrentMenu();\n          clearSupport();\n        }\n\n        if (document.readyState === \"loading\") document.addEventListener(\"DOMContentLoaded\", init);\n        else init();\n\n      })();\n    <\/script>\n\n  <\/section>\n<\/div>\n","protected":false},"excerpt":{"rendered":"<p>Overview Section 1 Section 2 Section 3 Section 4 Reading Speaking Writing IELTS Listening \u2013 Section 3 (Questions 21\u201330): Library<\/p>\n","protected":false},"author":1,"featured_media":441,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"colormag_page_layout":"default_layout","footnotes":""},"categories":[25,28,27],"tags":[],"class_list":["post-466","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-ielts","category-listening","category-test-1"],"_links":{"self":[{"href":"https:\/\/i-cte.org\/robot\/wp-json\/wp\/v2\/posts\/466","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/i-cte.org\/robot\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/i-cte.org\/robot\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/i-cte.org\/robot\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/i-cte.org\/robot\/wp-json\/wp\/v2\/comments?post=466"}],"version-history":[{"count":3,"href":"https:\/\/i-cte.org\/robot\/wp-json\/wp\/v2\/posts\/466\/revisions"}],"predecessor-version":[{"id":487,"href":"https:\/\/i-cte.org\/robot\/wp-json\/wp\/v2\/posts\/466\/revisions\/487"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/i-cte.org\/robot\/wp-json\/wp\/v2\/media\/441"}],"wp:attachment":[{"href":"https:\/\/i-cte.org\/robot\/wp-json\/wp\/v2\/media?parent=466"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/i-cte.org\/robot\/wp-json\/wp\/v2\/categories?post=466"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/i-cte.org\/robot\/wp-json\/wp\/v2\/tags?post=466"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}