打开模态框的第二个按钮在第一次单击时没有响应并且无法正确关闭

问题描述 投票:0回答:1

我正在开发一个项目,用户需要使用签名板签署表单。该表单需要三个单独的签名,我已经实现了三个按钮来打开签名板的模式。但是,我在使用第二个按钮时遇到了问题:

当我单击第二个按钮打开其模式时,第一次单击时它不会打开。仅在第二次单击后才打开。 一旦模式打开,它就无法正确关闭。 此问题仅发生在第二个按钮上,无论单击按钮的顺序如何。第一个和第三个按钮对于打开和关闭各自的模态效果非常好。

我怀疑我的代码中可能存在与事件处理或模式初始化相关的问题,但我不确定是什么导致了这种不一致。

这是我的按钮代码片段:

<tr>
    <td>
        <label for="candidate_sign">Tandatangan</label>
        <button type="button" class="btn btn-primary" data-toggle="modal" data-target="#signatureModal" data-user="candidate">Add Signature</button>
        <input type="hidden" name="candidate_signature" id="candidate_signature" value="<?= htmlspecialchars($form_data['candidate_signature'] ?? '') ?>">
        <div id="candidate-signature-container" class="signature-container">
            <!-- The signature that been saved will be placed here -->
            <?php if (!empty($form_data['candidate_signature'])): ?>
                <img src="<?= htmlspecialchars($form_data['candidate_signature']); ?>" alt="Candidate Signature" class="signature-img">
            <?php endif; ?>
        </div>
    </td>
    <td>
        <label for="hr_sign">Tandatangan</label>
        <button type="button" class="btn btn-primary" data-toggle="modal" data-target="#signatureModal" data-user="hr">Add Signature</button>
        <input type="hidden" name="hr_signature" id="hr_signature" value="<?= htmlspecialchars($form_data['hr_signature'] ?? '') ?>">
        <div id="hr-signature-container" class="signature-container">
            <!-- HR signature will be displayed here -->
            <?php if (!empty($form_data['hr_signature'])): ?>
                <img src="<?= htmlspecialchars($form_data['hr_signature']); ?>" alt="HR Signature" class="signature-img">
            <?php endif; ?>
        </div>
    </td>
    <td>
        <label for="comben_sign">Tandatangan</label>
        <button type="button" class="btn btn-primary" data-toggle="modal" data-target="#signatureModal" data-user="comben">Add Signature</button>
        <input type="hidden" name="comben_signature" id="comben_signature" value="<?= htmlspecialchars($form_data['comben_signature'] ?? '') ?>">
        <div id="comben-signature-container" class="signature-container">
            <!-- Comben signature will be displayed here -->
            <?php if (!empty($form_data['comben_signature'])): ?>
                <img src="<?= htmlspecialchars($form_data['comben_signature']); ?>" alt="Comben Signature" class="signature-img">
            <?php endif; ?>
        </div>
    </td>
</tr>

此片段适用于模态框:

<div class="modal" id="signatureModal" tabindex="-1" role="dialog" aria-labelledby="signature" aria-hidden="true">
    <div class="modal-dialog modal-xl">
        <div class="modal-content" style="width: 100%; max-width:100%;">
            <div class="modal-header">
                <h4 class="modal-title"  style="display: inline-block; vertical-align: middle;">Electronic Signature</h4>
                <button type="button" class="close" data-dismiss="modal" aria-label="Close" style="float: right; margin-top: -5px;">
                    <span aria-hidden="true">&times;</span>
                </button>
            </div>
            <div class="modal-body">
                <!-- Tab navigation -->
                <ul class="nav nav-tabs" id="signatureTab">
                    <li class="active">
                        <a href="#add-signature" data-toggle="tab">Add Signature</a>
                    </li>
                </ul>
                
                <!-- Tab contents -->
                <div class="tab-content" id="signatureTabContent">
                    <!-- Add Signature Tab -->
                    <div class="tab-pane active" id="add-signature">
                        <canvas id="signature-pad" class="signature-pad border bg-white" style="width: 100%; height: 500px; border: 1px solid #ccc;"></canvas>
                        <p class="text-muted small">*Your signature will be saved in the database.</p>
                    </div>
                </div>

                <div class="modal-footer">
                    <div class="pull-left">
                        <button type="button" class="btn btn-info" id="undo">Undo</button>
                        <button type="button" class="btn btn-danger" id="clear">Clear</button>
                        <button type="button" class="btn btn-primary" id="done">Done</button>
                    </div>
                </div>
            </div>
        </div>
    </div>
</div> 

这是函数的片段:

var $j = jQuery.noConflict();

document.addEventListener("DOMContentLoaded", () => {
    const canvas = document.getElementById('signature-pad');
    const clearButton = document.querySelector('#clear');
    const undoButton = document.querySelector('#undo');
    const doneButton = document.querySelector('#done');
    let currentUserType = ''; // To track the current user type (candidate, hr, or comben)

    // jQuery-specific logic
    $j(() => {
        // Initialize tabs
        $j('.nav-tabs a').tab();

        // Track which button triggered the modal
        $j('button[data-target="#signatureModal"]').on("click", function () {
            currentUserType = $j(this).data("user"); // Set current user type
            updateSignatureButtonText(currentUserType); // Update button text for the specific user
            $j('#signatureTab a[href="#add-signature"]').tab('show'); // Show the add signature tab
        });

        // Resize canvas when modal is shown
        $j("#signatureModal").on("shown.bs.modal", resizeCanvas);
        $j(window).on("resize", resizeCanvas);
    });

    const signaturePad = new SignaturePad(canvas, {
        backgroundColor: null,
        penColor: 'black',
        lineWidth: 10
    });

    function resizeCanvas() {
        const ratio = Math.max(window.devicePixelRatio || 1, 1);
        canvas.width = canvas.offsetWidth * ratio;
        canvas.height = canvas.offsetHeight * ratio;
        canvas.getContext("2d").scale(ratio, ratio);
        signaturePad.clear();
    }

    function closeModal() {
        $j('#signatureModal').on('shown.bs.modal', function() {
            $j("#signatureModal").modal("hide");
        });
    }

    clearButton.addEventListener('click', () => signaturePad.clear());

    undoButton.addEventListener('click', () => {
        const data = signaturePad.toData();
        if (data.length > 0) {
            data.pop();
            signaturePad.fromData(data);
        }
    });

    doneButton.addEventListener("click", function () {
        if (signaturePad.isEmpty()) {
            alert("Please provide a signature first.");
            return;
        }

        const dataURL = signaturePad.toDataURL("image/svg+xml");
        displayRecentSignature(dataURL, currentUserType);
        closeModal();
    });

    // Function to display the signature
    function displayRecentSignature(dataURL, userType) {
        const containerId = `${userType}-signature-container`; // Dynamically determine the container
        const recentSignatureContainer = document.getElementById(containerId);

        if (!recentSignatureContainer) {
            console.error(`Signature container for ${userType} not found`);
            return; // Exit if the container doesn't exist
        }

        // Clear previous signature in the specific container
        recentSignatureContainer.innerHTML = "";

        const img = document.createElement("img");
        img.src = dataURL;
        img.alt = "Recent Signature";
        img.classList.add("recent-signature");
        img.style.width = "150px";
        img.style.height = "auto";

        recentSignatureContainer.appendChild(img);

        const hiddenInput = document.getElementById(`${userType}_signature`);
        hiddenInput.value = dataURL;

        // Update button text to "Edit Signature" after signature is added
        updateSignatureButtonText(userType);
    }

    // Function to update the signature button text
    function updateSignatureButtonText(userType) {
        const button = document.querySelector(`button[data-user="${userType}"]`);

        if (!button) {
            console.error(`Button for ${userType} not found`);
            return; // Exit if the button doesn't exist
        }

        const signatureField = document.getElementById(`${userType}_signature`).value;

        // Check if the signature field has a value and update the button text accordingly
        if (signatureField && signatureField.trim() !== "") {
            button.textContent = "Edit Signature"; // Change button text if signature exists
        } else {
            button.textContent = "Add Signature"; // Default button text if no signature
        }
    }

    // Call the function on page load to set the initial button text
    ["candidate", "hr", "comben"].forEach(userType => {
        updateSignatureButtonText(userType);
    });
});

我尝试了以下方法来解决这个问题:

  • 使用 .on('click') 和 .off('click') 来处理按钮点击和模态事件。
  • 添加console.log语句来调试问题。日志显示按钮被单击,模式打开,并按预期关闭。然而,实际上,第一次单击第二个按钮时,模式不会打开,也不会正确关闭。
  • 我尝试添加超时以强制模式在一段时间后隐藏,但这也没有解决问题。

我的期望:

  • 单击任何按钮时,模式应立即打开。
  • 单击关闭按钮时,模式应正确关闭。

实际发生的事情:

  • 第二个按钮第一次需要单击两次才能打开其模式。
  • 打开后,第二个按钮的模式不会按预期关闭。
php html jquery twitter-bootstrap-3 bootstrap-modal
1个回答
0
投票

在此处的代码中,您在

shown.bs.modal
事件上添加一个新的事件侦听器。

function closeModal() {
    $j('#signatureModal').on('shown.bs.modal', function() {
        $j("#signatureModal").modal("hide");
    });
}

我认为然后监听模式显示(第二次单击),然后立即再次关闭它。也许将其更改为

function closeModal() {
    $j("#signatureModal").modal("hide");
}
© www.soinside.com 2019 - 2024. All rights reserved.