select element inside a table after creating it with ajax call

I have an unput field and some functions. This input field makes an ajax call, returns a table and inserts it onto the page. This table has editable fields and a save button.

Functions I have don’t seem to work with this returned table. I think it is because functions existed before the table and are not aware of it?

How can I make the pre-existing functions aware of the new table and its elements? Or what is the correct way to work with the new table?

JsSIP “peerconnection” Event Not Firing for Outbound Calls – Why and How to Fix?

I’m building a web-based SIP phone application using JsSIP (version 3.10.0) to handle VoIP calls over WebRTC. My setup works fine for inbound calls—audio streams both ways—but I’m facing an issue with outbound calls where I can’t hear the remote party, and the “peerconnection” event isn’t firing as expected.

What I’m Doing

Setup: I’m using JsSIP to connect to a SIP server via WebSocket (WSS). The client registers successfully and can initiate/receive calls.
Code Structure: I handle all new sessions (inbound and outbound) in a handleNewRTCSession function triggered by the “newRTCSession” event from JsSIP’s UA. For WebRTC, I rely on the “peerconnection” event to access the RTCPeerConnection and attach a “track” listener to capture the remote audio stream.
Outbound Call Flow: I call userAgent.call(target, callOptions) to start an outbound call. The call connects (remote party answers), and they can hear me, but I don’t hear them.

 const userAgent = new JsSIP.UA({
  uri: "sip:[email protected]",
  password: "****",
  sockets: [new JsSIP.WebSocketInterface("wss://sip-server.example.com:7443")],
});

const callOptions = {
  mediaConstraints: { audio: true, video: false },
  pcConfig: { iceServers: [{ urls: "stun:stun.l.google.com:19302" }] },
};

userAgent.on("newRTCSession", handleNewRTCSession);

function handleNewRTCSession(e) {
  const session = e.session;
  console.log("New session:", session.direction);

  session.on("peerconnection", (data) => {
    console.log("Peerconnection event:", data);
    const peerConnection = data.peerconnection;
    peerConnection.addEventListener("track", (event) => {
      console.log("Remote stream received:", event.streams[0]);
      document.getElementById("remoteAudio").srcObject = event.streams[0];
    });
  });

  session.on("accepted", () => {
    console.log("Call accepted");
  });

  session.on("failed", (e) => {
    console.log("Call failed:", e.cause);
  });

  if (session.direction === "outgoing") {
    console.log("Outbound call started");
  }
}

function makeCall(target) {
  userAgent.call(target, callOptions);
}

// Start UA
userAgent.start();

The Workaround which i’m trying right now is forcing peerconnection when the call is accepted in outbound case:

   if (session.connection && session.direction === óutgoing) {
          console.log("Manually handling peer connection:", session.connection);
          handlePeerConnection({ peerconnection: session.connection });
        }

function handlePeerConnection(data) {
  console.log(data);
  const peerConnection = data.peerconnection;
  peerConnection.addEventListener("track", (event) => {
    console.log(event);
    console.log("StreamViewType", event.streams);
    const remoteStream = event.streams[0];
    console.log("Remote stream received:", remoteStream);
    audioElement.srcObject = remoteStream;
    audioElement
      .play()
      .catch((e) => console.error("Audio playback failed:", e));
  });

  peerConnection.addEventListener("icecandidate", (event) => {
    if (event.candidate) {
      console.log("ICE candidate:", event.candidate);
    } else {
      console.log("ICE gathering complete");
    }
  });
}

Questions

  1. Why isn’t the “peerconnection” event firing for outbound calls in
    JsSIP 3.10.0, even though the call connects and session.connection
    exists?
  2. Is this a known bug, a configuration issue, or something specific to
    my SIP server’s SDP/ICE handling?
  3. Is manually using session.connection a safe long-term solution, or
    should I adjust my approach (e.g., update JsSIP, change
    callOptions)?

Additional Details

JsSIP Version: 3.10.0

Browser: Chrome (latest)

SIP Server: A hosted FusionPBX.

SDP: Local offers Opus/G722/PCMU, remote responds with G722, both sendrecv.

I’d appreciate any insights or suggestions to fix this cleanly without relying on the workaround. Thanks!

Jodit inline toolbar auto-open

Is there a way to keep Jodit’s inline toolbar open (if there’s selected text) after a choice is made from the toolbar? If not, is there a way to auto-open the inline toolbar if currently there’s selected text?

Currently the toolbar closes any time a choice is made – this means if I need to apply multiple settings to a selection I need to make the same selection that many times.

Using Typescript library in a Kotlin project

I have a lib written in typescript that I need to run on an existing Kotlin project for an Android app. How can I use this lib? I read some documentation but I didn’t understand it, I need some detailed explanation or example. I can get this lib from nexus or from my files since I’ve already downloaded it, so I can use it from wherever you think it’s easier. To be honest I’m completely lost but if it helps, all the ts files that I downloaded had .d on it (like file.d.ts), I don’t know if that means I still have to compile it to js to be able to use it. There is also an index.js file. I’m open to hear any suggestion on how to proceed with this.

What does the lit element checksize script do?

Lit Element has a typescript starter project that has a package.json checksize script and it looks like this.

"checksize": "rollup -c ; cat my-element.bundled.js | gzip -9 | wc -c ; rm my-element.bundled.js"

The rollup -c part produces a nice report that shows the size of the bundle like this:

┌───────────────────────┬──────────┐
│ File name             │ Size     │
│ --------------------- │ -------- │
│ my-element.bundled.js │ 17.07 kB │
│ --------------------- │ -------- │
│ Totals                │ 17.07 kB │

And I’m trying to figure out what the cat my-element.bundled.js | gzip -9 | wc -c part is for.

It produces a number. How do we interpret that number?

For example without changing the lit sample project at all this is the output produced by running checksize:

┌───────────────────────┬──────────┐
│ File name             │ Size     │
│ --------------------- │ -------- │
│ my-element.bundled.js │ 17.07 kB │
│ --------------------- │ -------- │
│ Totals                │ 17.07 kB │
└───────────────────────┴──────────┘
    6325

What is the number 6325?

content not stretching a 100vh

I have site that I am working on all of my content is inside a main-container div and I want the content to always stretch to a 100vh, but I can’t seem to get it working correctly. my main-container is just a div but each section and the footer are their own flexboxes.

Here is the HTML:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <script src="scripts/copyrightScript.js"></script>
    <script src="https://cdn.jsdelivr.net/npm/@splidejs/[email protected]/dist/js/splide.min.js"></script>
    <script src="scripts/splide.js"></script>
    <script src="https://kit.fontawesome.com/26a63f0e22.js" crossorigin="anonymous"></script>
    <link rel="stylesheet" href="styles.css">
    <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@splidejs/[email protected]/dist/css/splide.min.css">

    <title>Mario Shamhon Portfolio</title>
</head>
<body>
    <div id="main-container">
        <header>
            <nav>
                <div class="nav-left-side">
                    <a href="#about-me-section"> Mario Shamhon</a>
                </div>
                <ul class="nav-right-side">
                    <li><a href="#about-me-section"> About me</a></li>
                    <li><a href="#projects-section"> Projects</a></li>
                    <li><a href="#skills-section"> Skills</a></li>
                </ul>
            </nav>
        </header>

        <section id="about-me-section">
            <h2>Hi everyone I'm Mario</h2>
            <div class="headshot">
                <picture>
                    <img src="images/headshot.jpg" alt="headshot">
                </picture>
            </div>
            <div class="bio">
                <p>
                    Hi all! I'm Mario I recently graduated from San Diego State University with a masters degree in computer Science I really enjoy 
                    all types of software development I am always experimenting to learn new technologies and programming languages. We can only fail if we don't 
                    try!   
                </p>
                <br>
                <p>
                    Apart from coding I enjoy working out or trying out new restaurants  
                </p>
            </div>
            <div class="social-links">
                <a href="https://github.com/marioshamhon" target="_blank">
                    <i class="fa-brands fa-github"></i>
                </a>
                <a href="https://www.linkedin.com/in/mario-shamhon-2224a9b7/" target="_blank">
                    <i class="fa-brands fa-linkedin"></i>
                </a>
            </div>
        </section>

        <div class="projects-skills-container">
            <section id="projects-section">
                <h2>ProJects</h2>
                <!-- Swiper Container -->
                <div class="splide" id="project-slider" role="group" aria-label="Splide Basic HTML Example">
                    <div class="splide__track">
                        <ul class="splide__list">
                        <!-- Project 1 -->
                            <li class="splide__slide">
                                <div class="project-card">
                                    <a href="https://github.com/marioshamhon/cs648assignment13/" target="_blank">
                                        <img src="images/inventory_management_project.webp" alt="Inventory Management System: React">
                                        <h3>Inventory Management System: React </h3>
                                        <p>
                                            This is an Inventory Management System made using React as the frontend and Express Server 
                                            along with MongoDB for the backend. You can view, add, delete, or update product inventory
                                            that are all managed a database I created using MongoDB. 
                                        </p>
                                    </a>    
                                </div>
                            </li>
                            <!-- Project 2 -->
                            <li class="splide__slide">
                                <div class="project-card">
                                    <a href="https://github.com/marioshamhon/RedNosePirate/" target="_blank">
                                        <img src="images/red_nose_project.webp" alt="Red Nose Pirate">
                                        <h3>Red Nose Pirate: C#</h3>
                                        <p>
                                            This was a platformer game I developed with a group of my peers.  
                                            I was responsible for level design and enemy character programming and behavior.
                                        </p>
                                    </a>    
                                </div>
                            </li>
                            <!-- Project 3 -->
                            <li class="splide__slide">
                                <div class="project-card">
                                    <a href="https://github.com/marioshamhon/CS-570-Linux-shell-clone/" target="_blank">
                                        <img src="images/shell_clone_project.webp" alt="Linux Shell Clone: C">
                                        <h3>Linux Shell Clone: C</h3>
                                        <p>
                                            Developed a functional clone of the Linux shell using C programming language. Implemented features: valid 
                                            command execution, input/output redirection, pipeline commands, and background commandexecution. Created custom built-in 
                                            functionalities, including directory changing and error checking. Utilized system calls to ensure correct shell functionality.
                                        </p>
                                    </a>    
                                </div>
                            </li>
                        </ul>
                    </div>
                </div>
            </section>
        
            <section id="skills-section">
                <h2>Skills</h2>
                <div class="skills-icons-container">
                    <i class="fa-brands fa-python"></i>
                    <i class="fa-brands fa-java"></i>
                    <i class="fa-solid fa-database"></i>
                    <i class="fa-brands fa-react"></i>
                    <i class="fa-brands fa-js"></i>
                    <i class="fa-brands fa-bootstrap"></i>
                </div>
            </section>
        </div>
        
        <footer>
            <p>&copy; <span id="year"></span> Mario Shamhon. All Rights Reserved</p>
        </footer>
    </div>
</body>
</html>

Here is the CSS:

/* VARIABLES */
:root {
    --background-color: #74C0FC;
    --headings-and-links-color: #1a1c20;
    --sections-background-color: #f8f8f8;
    --link-hover-color: #ffffff;
    --project-card-background-color: #DFDFDF;
}

/* RESET BROWSER  DEFAULTS */
* {
    margin: 0;
    padding: 0;
    box-sizing: border-box;
}

 @font-face {
    font-family: "Sour Gummy";
    src: url(fonts/SourGummy-Italic-VariableFont_wdth,wght.ttf);
 }   


body{
    font-family: "Sour Gummy", sans-serif;
}

#main-container {
    margin: 0 auto;
    max-width: 1200px;
    width: 90%; 
    height: 100vh;  
}

a {
    color: var(--headings-and-links-color);
    text-decoration: none;
}

nav {
    background-color: var(--background-color);
    display: flex;
    justify-content: space-between;
    height: 5rem;
    align-items: center;
    padding: 0 3.125rem;
}

nav .nav-right-side {
    display: flex;
    list-style: none;
}

nav .nav-left-side a {
    font-size: 1.5rem;
    font-weight: 600;
}

nav .nav-right-side a {
    font-size: 1rem;
    font-weight: 600;
    margin: 0 0.625rem;
}

nav .nav-right-side a:hover {
    color: var(--link-hover-color)
}

/* General Section Styles */
section {
    display: flex;
    flex-direction: column;
    align-items: center;
    background-color: var(--sections-background-color);
}

/* Section Heading Styles */
section h2 {
    font-size: 3rem;
    font-weight: 700;
    color: var(--headings-and-links-color);
}

#about-me-section {
    padding: 0 2rem;
    margin-bottom: 2rem;
    border-radius: 0 0 10px 10px;
}

#about-me-section .headshot {
    width: 20rem;
    height: 20rem;
    margin-top: 1rem;
    margin-bottom: 2.4rem;
    border-radius: 50%;
    box-shadow: 0 10px 20px rgba(0, 0, 0, 0.2);
}

#about-me-section .headshot img {
    width: 100%;
    height: 100%;
    border-radius: 50%;
    object-fit: cover;
    object-position: top; /* Moves the image upwards so the head is more visible */
    transition: transform 0.3s ease;
}

#about-me-section .headshot img:hover {
    transform: scale(1.05);
}

#about-me-section .bio p {
    font-size: 1.25rem;
    font-weight: 300;
    text-align: center;
}

#about-me-section .social-links {
    font-size: 3rem;
}

#about-me-section .social-links i {
    color: var(--background-color);
}

#about-me-section .social-links a {
    margin: 0 0.75rem;
}

.projects-skills-container {
    display: grid;
    grid-template-columns: 1fr 1fr;
    column-gap: 2rem;
}

#projects-section, #skills-section {
    border-radius: 10px 10px 0 0;
    padding: 0 2rem;
    gap: 0.625rem;
}

.skills-icons-container {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 1.3rem;
} 

.skills-icons-container i {
    color: var(--background-color);
    font-size: 3rem; 
} 

.project-card {
    border-radius: 10px;
    box-shadow: 0 4px 8px rgba(0, 0, 0, 0.1);
    transition: transform 0.3s ease;
    text-align: center;
    background-color: var(--project-card-background-color);
}

.project-card:hover {
    transform: scale(1.05);
}

.project-card img {
    width: 100%;
    max-height: 12.5rem;
    object-fit: cover;
    border-radius: 10px;
}

.project-card h3 {
    margin-top: 1rem;
    font-size: 1.4rem;
}

.project-card p {
    font-size: 1rem;
    padding: 1rem 1rem;
}

footer {
    display: flex;
    justify-content: center;
    background-color:  var(--background-color);
    color: var(--headings-and-links-color);
    padding: 1rem 0;
    font-size: 0.875rem;
}

/* TABLETS IN LANDSCAPE */
@media (max-width: 71rem) {
    /* 1127px / 16px = 71rem */
    /* 71rem * 16px = 1136px */

    html {
        /* 12px / 16px = 75% */
        /* font-size: 87.5%; */
    }
}

/* TABLETS IN PORTRAIT */
@media (max-width: 56.6875rem) {
    /* 907 /16px = 56.6875rem */
    /* 56.6875 * 16px = 907px */
    /* I chose this breakpoint because this where 
       the two start have different widths */

    html {
        /* 10px / 16px = 50% */
        /* font-size: 62.5%; */
    }

    #about-me-section, #projects-section, #skills-section {
        padding: 1.25rem 2rem; 
    }

    .projects-skills-container {
        grid-template-columns: 1fr;
        row-gap: 2rem;
    }

    .skills-icons-container {
        flex-direction: row;
        justify-content: space-evenly;
        width: 100%;
    } 

    #projects-section {
        border-radius: 10px;
    }
}

/* MOBILE'S IN PORTRAIT & LANDSCAPE */
@media (max-width: 36rem) {
    /* 576px /16px = 36rem */
    /* 36rem * 16px = 576px */

    html {
        /* 9px / 16px = 56.25% */
        font-size: 56.25%;
    }
}

Here is the JavaScript file for slideshow:

document.addEventListener( 'DOMContentLoaded', function() {
    var splide = new Splide( '.splide', {
      pagination: false,
    });
    splide.mount();
  } );

On Slick Carousel how to center the slick-slide items if its less than three?

Here are what going to happen. If the condition is (slideCount <=2 ) the slide items should be at the center of the container, but right now they are align to the right(run the code snippet below). I’m not sure if its possible using css or slick events/settings to dynamically count the items. I want it to be centered if the (slideCount <=2 ) like this.
slick

Notes that it is working if the slick-slide item is only one.

Below are my codes:

$(function() {
    $('.js-addons-builder-slick').each(function() {
        let slider = $(this);
        let slideCount = slider.children('.items').length; // Count the number of slides

        let slickOptions = {
            slidesToShow: 1,
            slidesToScroll: 1,
            autoplay: false,
            dots: true,
            infinite: false,
            arrows: true,
            centerPadding: '0px',
            variableWidth: true,
            touchThreshold: 100,
            rows: 0,
            responsive: [{
                breakpoint: 768,
                settings: {
                    draggable: true,
                    variableWidth: true,
                    dots: true,
                    arrows: true,
                    infinite: false,
                }
            }]
        };

        // Conditional settings based on slide count
        if (slideCount <=2 ) {
            slickOptions.centerMode = true;
        } else {
            slickOptions.centerMode = false;
        }

        slider.slick(slickOptions);
    });
});
    .mycontainer {
        max-width: 1400px;
        margin: auto;
        background: orange;
        padding: 10px 0;
    }
    .items {
        width: 340px;
        margin: 0 10px;
        text-align: center;
        border: 1px solid black;
        padding: 20px;
        box-sizing: border-box;
    }
    .slick-prev:before, .slick-next:before {
        color: black;
    }
<link href="https://cdn.jsdelivr.net/npm/[email protected]/slick/slick.css" rel="stylesheet"/>
<link href="https://cdn.jsdelivr.net/npm/[email protected]/slick/slick-theme.css" rel="stylesheet"/>
<script src="https://code.jquery.com/jquery-3.6.0.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/[email protected]/slick/slick.min.js"></script>

<div class="mycontainer">
    <div class="js-addons-builder-slick page-slick-flex">
        <div class="items">Slide 1</div>
        <div class="items">Slide 2</div>
    </div>

    <div class="js-addons-builder-slick page-slick-flex">
        <div class="items">Slide 1</div>
    </div>
</div>

IIS Application Pools cannot access Google Drive shortcuts [closed]

I have a folder from Google Drive account A that is shared with Google Drive account B. From account B, I created a shortcut for this folder. I installed Google Drive B on my computer, and from here, my web application on IIS will access this shortcut to read data. However, the problem is that the Application Pools do not have sufficient permissions to access it, even though I have set full control for the shortcut with IIS_IUSRS. It only works if I use the Admin account that is running this Google Drive, but this requires the Admin account to have a password. I need to figure out how to set permissions so that the Application Pools can also access it, or use the Admin account for identity without requiring a password. Alternatively, I can adjust the code if needed.enter code here

JQuery Inputmask large and negative time values

I’m trying to configure inputmask to allow large and negative time values.

Examples:

  • 1:10
  • 10:20
  • 198:45
  • -20:00
  • -300:01
  • -0:01

I’ve found this for regular 24 time periods:

$(“input.timeedit”).inputmask({
alias: “datetime”,
inputFormat: “HH:mm” });

Which works great for a max 24 hours but does not go higher or allow negatives. Any suggestions on how to configure it?

O puppeteer não encontra os elementos da pagina independente do tempo [closed]

Estou criando um bot mas quando tento acessar as tags da pagina recebo null ou um array vazio, quando peço para esperar ele passa o tempo de espera e manda um erro:

    const browser = await puppeteer.launch({
    headless: false,
    defaultViewport: null,
    args: ['--start-maximized', '--no-sandbox', '--disable-setuid-sandbox'],
});
const page = await browser.newPage();

await page.goto('https://vera.bet.br/');

//Confirmar idade
await page.locator('.OFi5b').click();
await page.locator('#cookieConsentContainer > div > button.u9v7x').click();

//entrar na sessão de tênis
await page.goto('https://vera.bet.br/sports?sportId=6', { waitUntil: 'networkidle2' });
await new Promise(function (resolve, reject) {
    setTimeout(function () {
        resolve();
    }, 3000);
})

await page.waitForSelector('.eventlist_eu_fe_Selection_line .eventlist_eu_fe_TwoBoxTemplate_side1', {visible: true});
let allMatches = await page.$$('.eventlist_eu_fe_Selection_line .eventlist_eu_fe_TwoBoxTemplate_side1');

console.log(allMatches.length);
await allMatches[0].click();

MatterJS Ball Not Getting Affected by Gravity in SvelteKit Webapp

I’m trying to integrate a game, built with matter-js, into my existing SvelteKit webapp but am getting stumped as to why gravity is not affecting the circle body I’m adding. The following is the typescript code within my svelte file:

onMount(async () => {
  const Matter = await import('matter-js');
  const canvas = document.getElementById("canvas")!

  const engine = Matter.Engine.create();

  const ball = Matter.Bodies.circle(100, 0, 10);
  Matter.Composite.add(engine.world, ball);
  Matter.Engine.update(engine);

  const render = Matter.Render.create({
    element: canvas,
    engine: engine,
    })
  Matter.Render.run(render);
  Matter.Runner.run(engine);
})

The ball is stuck in the initial position set within the circle() method. I’m using vite for the local dev server.

Custom validation to exclude trailing spaces in text responses in Qualtrics

I’m building a Qualtrics form that requires a respondent to enter their email address. That question is a single line text entry question type. The email address being typed correctly matters because I have display logic that relies on specific email addresses, and that display logic fails when emails are entered with a trailing space. I anticipate my respondents will use their phones to answer the survey, and phones are notorious for leaving trailing spaces in open text fields.

Normally, I would use the “Email Address” content type validation choice under “Response Requirements” to enforce only valid email addresses to eliminate the trailing space issue. The issue here is that I have custom validation already implemented on that question. It requires the text to contains our organization’s specific email suffix. The question asks them to only enter email addresses with that suffix, but I don’t trust people to read and follow directions, so I wanted it to throw an error if another email suffix was detected and force them to fix the error.

Current Conditional Validation Logic:

IF: Q2 Please enter your business email (@org.com) 
>CONTAINS: "@org.com" 
>THEN: Validation passes

I tried adding another logical statement to the conditional validation logic above that would reject validation if a space was contained in the response, but it did not work:

Attempted Conditional Validation Logic:

IF: Q2 Please enter your business email (@org.com) 
>CONTAINS: "@org.com" AND
>DOES NOT CONTAIN: " "
>THEN: Validation passes

Other ideas I had were:

  • Changing the additional logical statement to match regex
  • JavaScript that prohibits spaces in that question’s responses
  • Converting to a form field type question to enforce validation

For the first two, I’m not sure how to approach the creation of a regex or JavaScript that would meet my needs. Any thoughts are appreciated.

Jquery: Dynamically adding code stored in a variable to events WITHOUT using eval()

I have a project which has a large number of controls (buttons, checkboxes, etc.) that I’m trying to find a way to add events to without directly putting the code in the html or in the main javascript/jquery file. Rather, I’d like to store the event code in a config file so that I can make changes if needed without having to touch the main code and so I don’t have a massive amount of repeating code just to assign actions.

The HTML has controls like this:

<id="elem1">
<id="elem2">
<id="elem3">
...

And then there is a separate JS config file which has an object like this:

btnAssign: [
    { el: '#elem1', onEvent: 'click', action: "someAction();" },
    { el: '#elem2', onEvent: 'change', action: "someOtherCode();someOtherCode2();" },
    { el: '#elem3', onEvent: 'click', action: "doSomethingElse();" }
    ...
    ]

What I want to do is now assign the “action” for the specified “onEvent” to the listed “el”. As an example, I want to add someAction(); to elem1‘s onclick event so that when I click on elem1, someAction(); gets executed.

In the main JS/Jquery file, the following works perfectly, but only if I use eval()

btnAssign.forEach((assignment) => {
    $(assignment.el).on(assignment.onEvent, function () {
        eval(assignment.action);
    });
});

Based on reading (https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/eval) I’d really like to find another way to accomplish this without the potential risks. I tried using indirect eval?. but some of the entries (not all) fail.

Is there a safer or better way to do this?

Create/generate a zip from user selections (website)

I’m in the process of overhauling my personal site for some small games/mods I made. I want to be able to have the users select what games and/or mods they want and generate a zip with said selections.

Basically, say I have GunGame, NoghtWalk, Banana City and VanillaBeans (fake names) available for download. User selects GunGame and VanillaBeans for downloading. I know I need to setup check boxes/click buttons for selections. But how would I go about generating a ZIP file with said selections?

Long story short, I have like 100 different versions of my files. I don’t want to have to upload and update 100 different files anytime there is an update. User selection and zip generation would save me TONS of time if I can figure it out.

I hope this makes sense to everyone. I know this is possible, as I’ve seen sites like this before. Unfortunately, it’s been about 15 years or more since I’ve messed with more than just basic HTML and the newer html5 is kinda kicking my butt. I appreciate any help anyone can give. Thanks in advance!

I tried about an hour of Google searching. Came across JSZip but not 100% sure how to implement it into my situation and I’m unsure of how to exactly use it.