OnClick с двумя вызовами функций занимает два щелчка, чтобы запустить обе функции JS - PullRequest
0 голосов
/ 06 ноября 2019

Вероятно, это будет помечено как дубликат, потому что по этому поводу уже так много вопросов SO, но я просто не могу применить ответы на эти вопросы к своему коду.

Я использую Razor,HTML, CSS и JavaScript в моем коде страницы хранения Blob.

С левой стороны на изображении ниже есть три контейнера. При нажатии на одного из них они должны открыться и показать всех своих детей (капли). В первый раз, когда я щелкаю один из контейнеров, запускается только один из вызовов функций (listContainerBlobs ()), а не тот, который открывает контейнер вверх (showHide ()).

enter image description here

Ниже приведен HTML-тег p, вызывающий функции onclick.

<p class="blob-container" onclick="showHide('@containerId', '@arrowId');listContainerBlobs('@jsonBlob', '@container.Name');"><i class="fa fa-caret-right" id="@arrowId"></i>  @container.Name</p>

Полный div с C # и бритвой:

 <aside class="aside">
    <div class="aside-header">

        <i class="fa fa-plus add-container-button aside-header-icons" onclick="addContainer()"></i><i class="fa fa-search search-button aside-header-icons"></i>
        <input id="searchBox" type="text" onkeyup="search()" name="search" placeholder="Search blobs..." />
    </div>
    <div class="aside-containers">
        @foreach (var container in containers)
        {
            caretArrowNumber++;
            string arrowId = "arrowId-" + caretArrowNumber;
            containerNumber++;
            string containerId = "containerId-" + containerNumber;
            var blobs = await Model.ListContainerBlobs(container.Name);
            //var jsonBlob = Json.Serialize(blobs);
            List<object> blobObject = new List<object>();
            blobObject.Add(new
            {
                blobCount = blobs.Count,
                blobs = blobs.Select(x => new
                {
                    Name = x.Name,
                    Container = container.Name,
                    Blobtype = x.BlobType,
                    Uri = x.Uri
                })
            });

            var jsonBlob = JsonConvert.SerializeObject(blobObject);

            <div class="arrow-blob-container">
                <p class="blob-container" onclick="showHide('@containerId', '@arrowId');listContainerBlobs('@jsonBlob', '@container.Name');"><i class="fa fa-caret-right" id="@arrowId"></i>  @container.Name</p>
            </div>
            <div class="showBlob" id="@containerId">
                <div class="ml-4">
                    @foreach (var blob in blobs)
                    {
                        blobNumber++;
                        string blobId = "blobId-" + blobNumber;
                        <div>
                            <input class="blobs" id="@blobId" type="button" value="@blob.Name" onclick="downloadBlob('@blobId', '@blob.Name', '@blob.Container.Name')" />
                        </div>
                    }
                </div>
            </div>

        }
    </div>
</aside>

Следующий коддве функции, вызываемые onclick:

<script>
function listContainerBlobs(json, container) {
    console.log("beginning");
    console.log(json);

    var arr = JSON.parse(json);

    console.log(arr);
    var blobs = document.getElementById('container-blob-display').innerHTML = "<h4>" + container + "</h4>";
    var otherDiv = document.getElementById('section-1');
    var thisDiv = document.getElementById('section-2');

    otherDiv.style.display = 'none';
    thisDiv.style.display = 'inline';

    var blobNumber = 0;

    for (i = 0; i < arr.length; i++){
        blobNumber++;
        var blobId = "blobId" + blobNumber;
        blobs += "<p class='search-result' id='" + blobId + "' onclick='downloadBlob('" + blobId + "', '" + arr[i].Name + "', '" + container + "')'>" + arr[i].Name + "</p>";
    }
    console.log(blobs);
}

function showHide(containerId, arrowId) {
    var c = document.getElementById(containerId);
    var a = document.getElementById(arrowId);

    if (c.style.display === "none") {
        c.style.display = "inline";
        a.className = "fa fa-caret-down";
    } else {
        c.style.display = "none";
        a.className = "fa fa-caret-right";
    }
}
</script>

Я пытался

  • закомментировать ListContainerBlobs() -функцию
  • закомментировать все css
  • изменен с style.display = "block" на "inline" (видно в примере кода)
  • переместил весь раздел скрипта в верхнюю часть html
  • , закомментированный почтивесь код в html, кроме самого необходимого

, но showHide() все равно не запускается при первом клике.

Таким образом, в настоящее время при первом щелчке запускается listContainerBlobs(), а при втором щелчке запускается showHide(), но я бы предпочел, чтобы они оба запускались при первом нажатии.

Iценим всю помощь, которую я могу получить! Заранее спасибо!

PS Я бы хотел сделать jsfiddle, но он, похоже, не понимает C # и List <> (думая, что <> - это тег)


Редактирование решения мистера Смита

Мне по-прежнему требуется два щелчка, чтобы запустить обе функции с этим решением мистера Смита:

HTML:

<div class="arrow-blob-container">
    <p class="blob-container aside-content" id="@newContId" data-containerId="@containerId" data-arrowId="@arrowId" data-jsonBlob="@jsonBlob" data-containerName="@container.Name"><i class="fa fa-caret-right" id="@arrowId"></i>  @container.Name</p>
</div>

Js:

document.querySelectorAll('.aside-content').forEach(element => {
    element.addEventListener('click', function (e) {
        let ds = this.dataset;

        showHide(ds.containerid, ds.arrowid);
        listContainerBlobs(ds.jsonblob, ds.containername);
    })
});

Это работает полностью с правильными идентификаторами и другими значениями, но, как я уже сказал, мне все еще нужно щелкнуть два раза, чтобы вызвать обе функции для вызова. Первый щелчок запускает listContainerBlobs(), второй щелчок showHide().

Есть идеи, почему это может быть?

1 Ответ

1 голос
/ 06 ноября 2019

Вы можете создать прослушиватель событий, который вызывает ваши функции:

<div class="arrow-blob-container">
    <p class="blob-container" data-container-id="@containerId" data-arrow-id="@arrowId" data-json-blob="@jsonBlob" data-container-name="@container.Name" ><i class="fa fa-caret-right" id="@arrowId"></i>  @container.Name</p>
</div>

Сценарий:

<script>
    document.querySelectorAll('.blob-container').forEach(element => {
        element.addEventListener('click', function(e) {
            let dataset = e.currentTarget.dataset;

            showHide(dataset.containerId, dataset.arrowId);
            listContainerBlobs(dataset.jsonBlob, dataset.containerName);
        });
    });
</script>

Проверьте этот фрагмент:

document.querySelectorAll('.blob-container').forEach(element => {
  element.addEventListener('click', function(e) {
    let dataset = e.currentTarget.dataset;

    console.log("containerId: " + dataset.containerId);
    console.log("arrowId: " + dataset.arrowId);
    console.log("jsonBlob: " + dataset.jsonBlob);
    console.log("containerName: " + dataset.containerName);
  });
});
<div class="arrow-blob-container">
  <button class="blob-container" data-container-id="container1" data-arrow-id="arrow1" data-json-blob="{...}" data-container-name="Button1">Display dataset</button>
  <button class="blob-container" data-container-id="container2" data-arrow-id="arrow2" data-json-blob="{...}" data-container-name="Button2">Display dataset</button>
  <button class="blob-container" data-container-id="container3" data-arrow-id="arrow3" data-json-blob="{...}" data-container-name="Button3">Display dataset</button>
  <button class="blob-container" data-container-id="container4" data-arrow-id="arrow4" data-json-blob="{...}" data-container-name="Button4">Display dataset</button>
</div>

Это также работает без querySelector, который может быть более понятным:

function onButtonClick(e) {
    let dataset = e.dataset;

    console.log("containerId: " + dataset.containerId);
    console.log("arrowId: " + dataset.arrowId);
    console.log("jsonBlob: " + dataset.jsonBlob);
    console.log("containerName: " + dataset.containerName);
}
<div class="arrow-blob-container">
  <button class="blob-container" onClick="onButtonClick(this)" data-container-id="container1" data-arrow-id="arrow1" data-json-blob="{...}" data-container-name="Button1">Display dataset</button>
  <button class="blob-container" onClick="onButtonClick(this)" data-container-id="container2" data-arrow-id="arrow2" data-json-blob="{...}" data-container-name="Button2">Display dataset</button>
  <button class="blob-container" onClick="onButtonClick(this)" data-container-id="container3" data-arrow-id="arrow3" data-json-blob="{...}" data-container-name="Button3">Display dataset</button>
  <button class="blob-container" onClick="onButtonClick(this)" data-container-id="container4" data-arrow-id="arrow4" data-json-blob="{...}" data-container-name="Button4">Display dataset</button>
</div>
...