{"id":3317,"date":"2024-02-08T10:10:34","date_gmt":"2024-02-08T10:10:34","guid":{"rendered":"https:\/\/startersites.io\/elementor\/garderobe\/?page_id=3317"},"modified":"2025-07-21T17:22:21","modified_gmt":"2025-07-21T17:22:21","slug":"services","status":"publish","type":"page","link":"https:\/\/booklystpress.com\/index.php\/services\/","title":{"rendered":"EduHub"},"content":{"rendered":"\t\t<div data-elementor-type=\"wp-page\" data-elementor-id=\"3317\" class=\"elementor elementor-3317\" data-elementor-post-type=\"page\">\n\t\t\t\t<div class=\"elementor-element elementor-element-7476c89 e-flex e-con-boxed e-con e-parent\" data-id=\"7476c89\" data-element_type=\"container\" data-e-type=\"container\">\n\t\t\t\t\t<div class=\"e-con-inner\">\n\t\t\t\t<div class=\"elementor-element elementor-element-1019402 elementor-widget elementor-widget-html\" data-id=\"1019402\" data-element_type=\"widget\" data-e-type=\"widget\" data-widget_type=\"html.default\">\n\t\t\t\t<div class=\"elementor-widget-container\">\n\t\t\t\t\t<!DOCTYPE html>\r\n<html lang=\"en\">\r\n<head>\r\n    <meta charset=\"UTF-8\">\r\n    <meta name=\"viewport\" content=\"width=device-width, initial-scale=1.0\">\r\n    <title>EduHub Digital Learning Resources<\/title>\r\n    <style>\r\n        * {\r\n            margin: 0;\r\n            padding: 0;\r\n            box-sizing: border-box;\r\n        }\r\n\r\n        body {\r\n            font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;\r\n            background-color: #f5f3f3;\r\n            line-height: 1.6;\r\n        }\r\n\r\n        .container {\r\n            width: 100%;\r\n            max-width: 1200px;\r\n            margin: 0 auto;\r\n            padding: 0 16px;\r\n        }\r\n\r\n        \/* Hero Section *\/\r\n        .hero {\r\n            background: linear-gradient(135deg, #264653 0%, #457b9d 100%);\r\n            padding: 64px 0;\r\n            color: white;\r\n        }\r\n\r\n        .hero-content {\r\n            display: grid;\r\n            grid-template-columns: 1fr;\r\n            gap: 32px;\r\n            align-items: center;\r\n        }\r\n\r\n        .hero-text h1 {\r\n            font-size: 36px;\r\n            font-weight: bold;\r\n            margin-bottom: 16px;\r\n            line-height: 1.2;\r\n            color: white !important;\r\n        }\r\n\r\n        .hero-text p {\r\n            opacity: 0.9;\r\n            margin-bottom: 32px;\r\n            font-size: 18px;\r\n        }\r\n\r\n        .search-container {\r\n            position: relative;\r\n            max-width: 384px;\r\n            margin-bottom: 24px;\r\n        }\r\n\r\n        .filters-container {\r\n            display: grid;\r\n            grid-template-columns: repeat(auto-fit, minmax(150px, 1fr));\r\n            gap: 12px;\r\n            max-width: 800px;\r\n            align-items: end;\r\n        }\r\n\r\n        .filter-group {\r\n            display: flex;\r\n            flex-direction: column;\r\n        }\r\n\r\n        .filter-select {\r\n            padding: 10px 12px;\r\n            border: 2px solid rgba(255, 255, 255, 0.3);\r\n            border-radius: 6px;\r\n            background: rgba(255, 255, 255, 0.9);\r\n            color: #4c4d4e;\r\n            font-size: 14px;\r\n            outline: none;\r\n            transition: all 0.3s ease;\r\n        }\r\n\r\n        .filter-select:focus {\r\n            border-color: #2a9d8f;\r\n            box-shadow: 0 0 0 3px rgba(42, 157, 143, 0.3);\r\n        }\r\n\r\n        .filter-btn {\r\n            padding: 10px 16px;\r\n            font-size: 14px;\r\n            white-space: nowrap;\r\n            border-radius: 6px;\r\n            cursor: pointer;\r\n            transition: all 0.3s ease;\r\n        }\r\n\r\n        .search-input {\r\n            width: 100%;\r\n            padding: 12px 16px 12px 48px;\r\n            border: none;\r\n            border-radius: 8px;\r\n            font-size: 16px;\r\n            background: white;\r\n            color: #4c4d4e;\r\n            outline: none;\r\n            transition: all 0.3s ease;\r\n        }\r\n\r\n        .search-input:focus {\r\n            box-shadow: 0 0 0 3px rgba(42, 157, 143, 0.3);\r\n        }\r\n\r\n        .search-icon {\r\n            position: absolute;\r\n            left: 16px;\r\n            top: 50%;\r\n            transform: translateY(-50%);\r\n            width: 20px;\r\n            height: 20px;\r\n            color: #747575;\r\n            pointer-events: none;\r\n        }\r\n\r\n        .hero-image {\r\n            height: 400px;\r\n            border-radius: 12px;\r\n            overflow: hidden;\r\n            background-image: url('https:\/\/booklystpress.com\/wp-content\/uploads\/2025\/06\/Eduhub-Photo-Poster.png');\r\n            background-size: cover;\r\n            background-position: center;\r\n            background-repeat: no-repeat;\r\n        }\r\n\r\n        \/* Media Gallery Section *\/\r\n        .media-gallery {\r\n            padding: 64px 0;\r\n        }\r\n\r\n        .gallery-header {\r\n            display: flex;\r\n            justify-content: space-between;\r\n            align-items: center;\r\n            margin-bottom: 32px;\r\n        }\r\n\r\n        .gallery-header h2 {\r\n            font-size: 24px;\r\n            font-weight: bold;\r\n            color: #4c4d4e;\r\n        }\r\n\r\n        .btn {\r\n            padding: 10px 20px;\r\n            border-radius: 6px;\r\n            text-decoration: none;\r\n            font-weight: 500;\r\n            transition: all 0.3s ease;\r\n            display: inline-block;\r\n            cursor: pointer;\r\n            border: none;\r\n            font-size: 14px;\r\n        }\r\n\r\n        .btn-outline {\r\n            background: transparent;\r\n            color: #264653;\r\n            border: 2px solid #264653;\r\n        }\r\n\r\n        .btn-outline:hover {\r\n            background: #264653;\r\n            color: white;\r\n        }\r\n\r\n        .btn-primary {\r\n            background: #d73237;\r\n            color: white;\r\n        }\r\n\r\n        .btn-primary:hover {\r\n            background: #c02a2f;\r\n        }\r\n\r\n        .btn-secondary {\r\n            background: #264653;\r\n            color: white;\r\n        }\r\n\r\n        .btn-secondary:hover {\r\n            background: #1e3a44;\r\n        }\r\n        \r\n        .btn-clear {\r\n            background: #f0f0f0;\r\n            color: #333;\r\n            border: 1px solid #ccc;\r\n        }\r\n        \r\n        .btn-clear:hover {\r\n            background: #e0e0e0;\r\n        }\r\n\r\n        .media-grid {\r\n            display: grid;\r\n            grid-template-columns: 1fr;\r\n            gap: 32px;\r\n        }\r\n\r\n        .media-card {\r\n            background: white;\r\n            border-radius: 12px;\r\n            box-shadow: 0 4px 6px rgba(0, 0, 0, 0.1);\r\n            overflow: hidden;\r\n            transition: transform 0.3s ease;\r\n        }\r\n\r\n        .media-card:hover {\r\n            transform: scale(1.02);\r\n        }\r\n\r\n        .media-image {\r\n            position: relative;\r\n            height: 192px;\r\n            background: linear-gradient(45deg, #457b9d, #2a9d8f);\r\n            display: flex;\r\n            align-items: center;\r\n            justify-content: center;\r\n            overflow: hidden;\r\n            cursor: pointer;\r\n        }\r\n\r\n        .media-overlay {\r\n            position: absolute;\r\n            top: 0;\r\n            left: 0;\r\n            right: 0;\r\n            bottom: 0;\r\n            background: rgba(0, 0, 0, 0.4);\r\n            display: flex;\r\n            align-items: center;\r\n            justify-content: center;\r\n            transition: background 0.3s ease;\r\n        }\r\n\r\n        .media-card:hover .media-overlay {\r\n            background: rgba(0, 0, 0, 0.3);\r\n        }\r\n\r\n        .play-icon {\r\n            width: 64px;\r\n            height: 64px;\r\n            background: rgba(255, 255, 255, 0.9);\r\n            border-radius: 50%;\r\n            display: flex;\r\n            align-items: center;\r\n            justify-content: center;\r\n            font-size: 24px;\r\n            color: #4c4d4e;\r\n            transition: all 0.3s ease;\r\n            cursor: pointer;\r\n        }\r\n\r\n        .play-icon:hover {\r\n            background: white;\r\n            transform: scale(1.1);\r\n        }\r\n\r\n        .duration-badge {\r\n            position: absolute;\r\n            bottom: 8px;\r\n            right: 8px;\r\n            background: rgba(0, 0, 0, 0.7);\r\n            color: white;\r\n            padding: 4px 8px;\r\n            border-radius: 4px;\r\n            font-size: 12px;\r\n        }\r\n\r\n        .media-content {\r\n            padding: 16px;\r\n        }\r\n\r\n        .media-content h3 {\r\n            font-weight: 600;\r\n            font-size: 18px;\r\n            color: #4c4d4e;\r\n            margin-bottom: 8px;\r\n        }\r\n\r\n        .media-meta {\r\n            font-size: 14px;\r\n            color: #747575;\r\n            display: flex;\r\n            gap: 12px;\r\n            flex-wrap: wrap;\r\n            margin-bottom: 8px;\r\n        }\r\n\r\n        .media-description {\r\n            font-size: 14px;\r\n            color: #666;\r\n            line-height: 1.4;\r\n            margin-bottom: 0;\r\n        }\r\n\r\n        .page-number {\r\n            background: #2a9d8f;\r\n            color: white;\r\n            padding: 2px 8px;\r\n            border-radius: 12px;\r\n            font-size: 12px;\r\n            font-weight: 500;\r\n        }\r\n\r\n        \/* Video modal styles *\/\r\n        .video-modal {\r\n            display: none;\r\n            position: fixed;\r\n            top: 0;\r\n            left: 0;\r\n            width: 100%;\r\n            height: 100%;\r\n            background: rgba(0, 0, 0, 0.9);\r\n            z-index: 1000;\r\n            align-items: center;\r\n            justify-content: center;\r\n        }\r\n\r\n        .video-modal.active {\r\n            display: flex;\r\n        }\r\n\r\n        .video-modal-content {\r\n            position: relative;\r\n            width: 90%;\r\n            max-width: 800px;\r\n            background: white;\r\n            border-radius: 12px;\r\n            overflow: hidden;\r\n        }\r\n\r\n        .video-modal-header {\r\n            padding: 20px;\r\n            border-bottom: 1px solid #e5e5e5;\r\n            display: flex;\r\n            justify-content: space-between;\r\n            align-items: center;\r\n        }\r\n\r\n        .video-modal-title {\r\n            font-size: 18px;\r\n            font-weight: 600;\r\n            color: #4c4d4e;\r\n            margin: 0;\r\n        }\r\n\r\n        .video-modal-close {\r\n            background: none;\r\n            border: none;\r\n            font-size: 24px;\r\n            cursor: pointer;\r\n            color: #747575;\r\n            padding: 0;\r\n            width: 30px;\r\n            height: 30px;\r\n            display: flex;\r\n            align-items: center;\r\n            justify-content: center;\r\n        }\r\n\r\n        .video-modal-body {\r\n            position: relative;\r\n            width: 100%;\r\n            height: 450px;\r\n        }\r\n\r\n        .video-modal iframe {\r\n            width: 100%;\r\n            height: 100%;\r\n            border: none;\r\n        }\r\n\r\n        .video-modal-info {\r\n            padding: 20px;\r\n            background: #f8f9fa;\r\n        }\r\n\r\n        \/* Loading and error states *\/\r\n        .loading-message {\r\n            grid-column: 1 \/ -1;\r\n            text-align: center;\r\n            padding: 40px;\r\n            color: #747575;\r\n            font-size: 18px;\r\n        }\r\n\r\n        .error-message {\r\n            grid-column: 1 \/ -1;\r\n            text-align: center;\r\n            padding: 40px;\r\n            color: #d73237;\r\n            background: rgba(215, 50, 55, 0.1);\r\n            border-radius: 8px;\r\n            margin: 20px 0;\r\n        }\r\n\r\n        .no-results {\r\n            grid-column: 1 \/ -1;\r\n            text-align: center;\r\n            padding: 40px;\r\n            color: #747575;\r\n        }\r\n\r\n        \/* Responsive Design *\/\r\n        @media (min-width: 768px) {\r\n            .container {\r\n                padding: 0 32px;\r\n            }\r\n\r\n            .hero-content {\r\n                grid-template-columns: 1fr 1fr;\r\n            }\r\n\r\n            .hero-text h1 {\r\n                font-size: 48px;\r\n            }\r\n\r\n            .media-grid {\r\n                grid-template-columns: repeat(2, 1fr);\r\n            }\r\n        }\r\n\r\n        @media (min-width: 1024px) {\r\n            .media-grid {\r\n                grid-template-columns: repeat(3, 1fr);\r\n            }\r\n        }\r\n\r\n        @media (max-width: 767px) {\r\n            .hero {\r\n                padding: 32px 0;\r\n            }\r\n\r\n            .hero-content {\r\n                grid-template-columns: 1fr;\r\n                gap: 24px;\r\n            }\r\n\r\n            .filters-container {\r\n                grid-template-columns: 1fr 1fr;\r\n            }\r\n\r\n            .filter-btn {\r\n                font-size: 12px;\r\n                padding: 8px;\r\n            }\r\n\r\n            .search-container {\r\n                max-width: 100%;\r\n            }\r\n\r\n            .search-input {\r\n                font-size: 14px;\r\n                padding-left: 44px;\r\n            }\r\n\r\n            .search-icon {\r\n                left: 14px;\r\n                width: 18px;\r\n                height: 18px;\r\n            }\r\n\r\n            .media-meta {\r\n                gap: 8px;\r\n            }\r\n        }\r\n    <\/style>\r\n<\/head>\r\n<body>\r\n    <!-- Hero Section -->\r\n    <section class=\"hero\">\r\n        <div class=\"container\">\r\n            <div class=\"hero-content\">\r\n                <div class=\"hero-text\">\r\n                    <h1>EduHub Digital Learning Resources<\/h1>\r\n                    <p>Discover comprehensive multimedia educational content designed to enhance learning experiences through interactive videos, virtual lab experiments, and integrated textbook materials.<\/p>\r\n                    <div class=\"search-container\">\r\n                        <svg class=\"search-icon\" fill=\"none\" stroke=\"currentColor\" viewBox=\"0 0 24 24\">\r\n                            <path stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"m21 21-6-6m2-5a7 7 0 1 1-14 0 7 7 0 0 1 14 0Z\"\/>\r\n                        <\/svg>\r\n                        <input type=\"text\" class=\"search-input\" placeholder=\"Search educational resources...\" id=\"search\">\r\n                    <\/div>\r\n                    \r\n                    <!-- Filters Section -->\r\n                    <div class=\"filters-container\">\r\n                        <div class=\"filter-group\">\r\n                            <select id=\"grade\" class=\"filter-select\">\r\n                                <option value=\"\">All Grades<\/option>\r\n                            <\/select>\r\n                        <\/div>\r\n                        <div class=\"filter-group\">\r\n                            <select id=\"subject\" class=\"filter-select\">\r\n                                <option value=\"\">All Subjects<\/option>\r\n                            <\/select>\r\n                        <\/div>\r\n                        <div class=\"filter-group\">\r\n                            <select id=\"topic\" class=\"filter-select\">\r\n                                <option value=\"\">All Topics<\/option>\r\n                            <\/select>\r\n                        <\/div>\r\n                        <div class=\"filter-group\">\r\n                            <select id=\"book_code\" class=\"filter-select\">\r\n                                <option value=\"\">All Books<\/option>\r\n                            <\/select>\r\n                        <\/div>\r\n                        <button class=\"btn btn-primary filter-btn\" id=\"applyFilters\">Apply Filters<\/button>\r\n                        <button class=\"btn btn-clear filter-btn\" id=\"clearFilters\">Clear All<\/button>\r\n                    <\/div>\r\n                <\/div>\r\n                <div class=\"hero-image\"><\/div>\r\n            <\/div>\r\n        <\/div>\r\n    <\/section>\r\n\r\n    <!-- Media Gallery Section -->\r\n    <section class=\"media-gallery\">\r\n        <div class=\"container\">\r\n            <div class=\"gallery-header\">\r\n                <h2>Educational Videos<\/h2>\r\n                <button class=\"btn btn-outline\" id=\"viewAllBtn\">View All<\/button>\r\n            <\/div>\r\n            <div class=\"media-grid\" id=\"videoGrid\">\r\n                <div class=\"loading-message\">Loading videos...<\/div>\r\n            <\/div>\r\n        <\/div>\r\n    <\/section>\r\n\r\n    <!-- Video Modal -->\r\n    <div class=\"video-modal\" id=\"videoModal\">\r\n        <div class=\"video-modal-content\">\r\n            <div class=\"video-modal-header\">\r\n                <h3 class=\"video-modal-title\" id=\"modalTitle\">Video Title<\/h3>\r\n                <button class=\"video-modal-close\" id=\"modalClose\">&times;<\/button>\r\n            <\/div>\r\n            <div class=\"video-modal-body\" id=\"modalEmbed\">\r\n                <!-- Video iframe will be inserted here -->\r\n            <\/div>\r\n            <div class=\"video-modal-info\" id=\"modalDescription\">\r\n                <!-- Video description will be inserted here -->\r\n            <\/div>\r\n        <\/div>\r\n    <\/div>\r\n\r\n    <script>\r\n        const apiURL = '\/wp-content\/themes\/blocksy-child\/eduhub-api.php';\r\n\r\n        function populateSelect(id, options) {\r\n            const select = document.getElementById(id);\r\n            \/\/ Keep the first option (All Grades\/Subjects\/etc)\r\n            const firstOption = select.options[0];\r\n            select.innerHTML = '';\r\n            select.appendChild(firstOption);\r\n            \r\n            options.forEach(opt => {\r\n                const option = document.createElement('option');\r\n                option.value = opt;\r\n                option.textContent = opt;\r\n                select.appendChild(option);\r\n            });\r\n        }\r\n\r\n        function getFilters() {\r\n            fetch(`${apiURL}?action=get_filters`)\r\n                .then(res => res.json())\r\n                .then(data => {\r\n                    populateSelect('grade', data.grade || []);\r\n                    populateSelect('subject', data.subject || []);\r\n                    populateSelect('topic', data.topic || []);\r\n                    populateSelect('book_code', data.book_code || []);\r\n\r\n                    \/\/ Apply URL filters after selects are populated\r\n                    initFromURL();\r\n                })\r\n                .catch(error => {\r\n                    console.error('Error loading filters:', error);\r\n                    initFromURL(); \/\/ Still try to load videos even if filters fail\r\n                });\r\n        }\r\n\r\n        function getSelectedFilters() {\r\n            return {\r\n                grade: document.getElementById('grade').value,\r\n                subject: document.getElementById('subject').value,\r\n                topic: document.getElementById('topic').value,\r\n                book_code: document.getElementById('book_code').value,\r\n                search: document.getElementById('search').value,\r\n            };\r\n        }\r\n\r\n        function loadVideos(page = 1) {\r\n            \/\/ Handle case where event object is passed accidentally\r\n            if (page instanceof Event || typeof page !== 'number') {\r\n                page = 1;\r\n            }\r\n            \r\n            const filters = getSelectedFilters();\r\n            const params = new URLSearchParams({ ...filters, action: 'get_videos', page, limit: 20 });\r\n            \r\n            fetch(`${apiURL}?${params.toString()}`)\r\n                .then(res => res.json())\r\n                .then(data => {\r\n                    const grid = document.getElementById('videoGrid');\r\n                    grid.innerHTML = '';\r\n                    \r\n                    if (!data || data.length === 0) {\r\n                        grid.innerHTML = '<div class=\"no-results\">No videos found matching your criteria. Try different filters.<\/div>';\r\n                        return;\r\n                    }\r\n                    \r\n                    data.forEach(video => {\r\n                        const card = document.createElement('div');\r\n                        card.className = 'media-card';\r\n                        \r\n                        \/\/ Build meta information with page number\r\n                        let metaItems = [];\r\n                        if (video.grade) metaItems.push(`<span>Grade: ${video.grade}<\/span>`);\r\n                        if (video.subject) metaItems.push(`<span>Subject: ${video.subject}<\/span>`);\r\n                        if (video.book_code) metaItems.push(`<span>Book: ${video.book_code}<\/span>`);\r\n                        if (video.page_number) metaItems.push(`<span class=\"page-number\">Page ${video.page_number}<\/span>`);\r\n                        \r\n                        card.innerHTML = `\r\n                            <div class=\"media-image\" onclick=\"openModalWithVideo(${video.id}, '${(video.media_title || '').replace(\/'\/g, \"\\\\'\")}', '${(video.description || '').replace(\/'\/g, \"\\\\'\")}', '${video.media_url}', '${video.media_source}')\">\r\n                                <div class=\"media-overlay\">\r\n                                    <div class=\"play-icon\">\u25b6<\/div>\r\n                                <\/div>\r\n                            <\/div>\r\n                            <div class=\"media-content\">\r\n                                <h3>${video.media_title || 'Untitled Video'}<\/h3>\r\n                                <div class=\"media-meta\">\r\n                                    ${metaItems.join(' ')}\r\n                                <\/div>\r\n                                <p class=\"media-description\">${video.description || 'No description available'}<\/p>\r\n                            <\/div>\r\n                        `;\r\n                        grid.appendChild(card);\r\n                    });\r\n                })\r\n                .catch(error => {\r\n                    console.error('Error loading videos:', error);\r\n                    document.getElementById('videoGrid').innerHTML = '<div class=\"error-message\">Error loading videos. Please try again.<\/div>';\r\n                });\r\n        }\r\n\r\n        function createEmbedFromUrl(mediaUrl, mediaSource) {\r\n            if (!mediaUrl) {\r\n                return '<p>No video URL available<\/p>';\r\n            }\r\n\r\n            \/\/ Handle different media sources\r\n            switch (mediaSource) {\r\n                case 'youtube':\r\n                    return createYouTubeEmbed(mediaUrl);\r\n                \r\n                case 'veed':\r\n                    return `<iframe src=\"${mediaUrl}\" width=\"100%\" height=\"400\" frameborder=\"0\" allowfullscreen><\/iframe>`;\r\n                \r\n                case 'webpage':\r\n                    return `<iframe src=\"${mediaUrl}\" width=\"100%\" height=\"400\" frameborder=\"0\" allowfullscreen><\/iframe>`;\r\n                \r\n                default:\r\n                    if (mediaUrl.match(\/\\.(mp4|webm|ogg|avi|mov)(\\?.*)?$\/i)) {\r\n                        return `<video controls width=\"100%\" height=\"400\">\r\n                            <source src=\"${mediaUrl}\" type=\"video\/mp4\">\r\n                            Your browser does not support the video tag.\r\n                        <\/video>`;\r\n                    }\r\n                    \r\n                    return `<iframe src=\"${mediaUrl}\" width=\"100%\" height=\"400\" frameborder=\"0\" allowfullscreen><\/iframe>`;\r\n            }\r\n        }\r\n\r\n        function createYouTubeEmbed(url) {\r\n            let videoId = null;\r\n            \r\n            const patterns = [\r\n                \/(?:youtube\\.com\\\/watch\\?v=)([a-zA-Z0-9_-]{11})\/,\r\n                \/(?:youtube\\.com\\\/embed\\\/)([a-zA-Z0-9_-]{11})\/,\r\n                \/(?:youtu\\.be\\\/)([a-zA-Z0-9_-]{11})\/,\r\n                \/(?:youtube\\.com\\\/v\\\/)([a-zA-Z0-9_-]{11})\/\r\n            ];\r\n            \r\n            for (const pattern of patterns) {\r\n                const match = url.match(pattern);\r\n                if (match) {\r\n                    videoId = match[1];\r\n                    break;\r\n                }\r\n            }\r\n            \r\n            if (videoId) {\r\n                return `<iframe width=\"100%\" height=\"100%\" src=\"https:\/\/www.youtube.com\/embed\/${videoId}\" frameborder=\"0\" allow=\"accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture\" allowfullscreen><\/iframe>`;\r\n            }\r\n            \r\n            return `<iframe src=\"${url}\" width=\"100%\" height=\"100%\" frameborder=\"0\" allowfullscreen><\/iframe>`;\r\n        }\r\n\r\n        function openModalWithVideo(videoId, title, description, mediaUrl, mediaSource) {\r\n            const modal = document.getElementById('videoModal');\r\n            const titleEl = document.getElementById('modalTitle');\r\n            const descEl = document.getElementById('modalDescription');\r\n            const embed = document.getElementById('modalEmbed');\r\n            \r\n            titleEl.textContent = title;\r\n            descEl.textContent = description;\r\n            \r\n            const embedCode = createEmbedFromUrl(mediaUrl, mediaSource);\r\n            embed.innerHTML = embedCode;\r\n            \r\n            modal.style.display = 'flex';\r\n        }\r\n\r\n        function closeModal() {\r\n            document.getElementById('videoModal').style.display = 'none';\r\n            document.getElementById('modalEmbed').innerHTML = '';\r\n        }\r\n\r\n        function clearFilters() {\r\n            \/\/ Reset all filter dropdowns\r\n            document.getElementById('grade').value = '';\r\n            document.getElementById('subject').value = '';\r\n            document.getElementById('topic').value = '';\r\n            document.getElementById('book_code').value = '';\r\n            document.getElementById('search').value = '';\r\n            \r\n            \/\/ Clear any URL parameters without reloading\r\n            if (window.history.replaceState) {\r\n                window.history.replaceState({}, document.title, window.location.pathname);\r\n            }\r\n            \r\n            \/\/ Reload videos with cleared filters\r\n            loadVideos();\r\n        }\r\n\r\n        function initFromURL() {\r\n            const params = new URLSearchParams(window.location.search);\r\n            const videoID = params.get('video_id');\r\n            const bookCode = params.get('book_code');\r\n\r\n            if (videoID) {\r\n                console.log('Loading video ID:', videoID);\r\n                fetch(`${apiURL}?action=get_video&video_id=${videoID}`)\r\n                    .then(res => res.json())\r\n                    .then(video => {\r\n                        console.log('Video data received:', video);\r\n                        \r\n                        if (!video || video.error) {\r\n                            alert('Video currently not available: ' + (video?.error || 'Video not found'));\r\n                            return;\r\n                        }\r\n\r\n                        if (video.status !== 'active') {\r\n                            alert('Video currently not available: ' + (video.message || 'Video has been removed or redirected'));\r\n                            return;\r\n                        }\r\n\r\n                        openModalWithVideo(\r\n                            video.id,\r\n                            video.media_title || 'Video',\r\n                            video.description || '',\r\n                            video.media_url,\r\n                            video.media_source\r\n                        );\r\n                    })\r\n                    .catch(error => {\r\n                        console.error('Error loading video:', error);\r\n                        alert('Error loading video: ' + error.message);\r\n                    });\r\n            } else if (bookCode) {\r\n                document.getElementById('book_code').value = bookCode;\r\n                loadVideos();\r\n            } else {\r\n                loadVideos();\r\n            }\r\n        }\r\n\r\n        \/\/ Event listeners\r\n        document.getElementById('grade').addEventListener('change', () => loadVideos());\r\n        document.getElementById('subject').addEventListener('change', () => loadVideos());\r\n        document.getElementById('topic').addEventListener('change', () => loadVideos());\r\n        document.getElementById('book_code').addEventListener('change', () => loadVideos());\r\n        document.getElementById('search').addEventListener('input', () => {\r\n            clearTimeout(window.searchTimeout);\r\n            window.searchTimeout = setTimeout(() => loadVideos(), 300);\r\n        });\r\n        document.getElementById('clearFilters').addEventListener('click', clearFilters);\r\n        document.getElementById('viewAllBtn').addEventListener('click', (e) => {\r\n            e.preventDefault();\r\n            clearFilters();\r\n        });\r\n        document.getElementById('modalClose').addEventListener('click', closeModal);\r\n        document.getElementById('videoModal').addEventListener('click', function(e) {\r\n            if (e.target === this) {\r\n                closeModal();\r\n            }\r\n        });\r\n\r\n        \/\/ Initialize when page loads\r\n        window.onload = () => {\r\n            getFilters();\r\n        };\r\n    <\/script>\r\n<\/body>\r\n<\/html>\t\t\t\t<\/div>\n\t\t\t\t<\/div>\n\t\t\t\t\t<\/div>\n\t\t\t\t<\/div>\n\t\t\t\t<\/div>\n\t\t","protected":false},"excerpt":{"rendered":"<p>EduHub Digital Learning Resources EduHub Digital Learning Resources Discover comprehensive multimedia educational content designed to enhance learning experiences through interactive videos, virtual lab experiments, and integrated textbook materials. All Grades All Subjects All Topics All Books Apply Filters Clear All Educational Videos View All Loading videos&#8230; Video Title &times;<\/p>\n","protected":false},"author":1,"featured_media":0,"parent":0,"menu_order":0,"comment_status":"closed","ping_status":"closed","template":"","meta":{"footnotes":""},"class_list":["post-3317","page","type-page","status-publish","hentry"],"blocksy_meta":{"has_hero_section":"disabled","vertical_spacing_source":"custom","content_area_spacing":"none","styles_descriptor":{"styles":{"desktop":"","tablet":"","mobile":""},"google_fonts":[],"version":6}},"_links":{"self":[{"href":"https:\/\/booklystpress.com\/index.php\/wp-json\/wp\/v2\/pages\/3317","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/booklystpress.com\/index.php\/wp-json\/wp\/v2\/pages"}],"about":[{"href":"https:\/\/booklystpress.com\/index.php\/wp-json\/wp\/v2\/types\/page"}],"author":[{"embeddable":true,"href":"https:\/\/booklystpress.com\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/booklystpress.com\/index.php\/wp-json\/wp\/v2\/comments?post=3317"}],"version-history":[{"count":116,"href":"https:\/\/booklystpress.com\/index.php\/wp-json\/wp\/v2\/pages\/3317\/revisions"}],"predecessor-version":[{"id":5697,"href":"https:\/\/booklystpress.com\/index.php\/wp-json\/wp\/v2\/pages\/3317\/revisions\/5697"}],"wp:attachment":[{"href":"https:\/\/booklystpress.com\/index.php\/wp-json\/wp\/v2\/media?parent=3317"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}