简体   繁体   English

切换按钮无法正常播放音频。 也是只播放一个音频元素的javascript代码

[英]toggle button not working properly for audio. also javascript code only playing one audio element

I have tried for hours to get this working but I am new to javascript so can't seem to solve it. 我已经尝试了几个小时才能使其正常工作,但是我对javascript还是陌生的,所以似乎无法解决。 There are two audio tags altogether in the html code below with two different mp3 files. 下面的html代码中共有两个音频标签,带有两个不同的mp3文件。 I have two questions here: 1. When I click on the label with class="play-bt" the audio does not play. 我在这里有两个问题:1.当我单击带有class =“ play-bt”的标签时,音频无法播放。 It only plays if I click near the label to the left hand top corner of the containing element. 仅当我单击包含元素左上角的标签附近时,它才会播放。 I would like it to start play when I click anywhere on the label. 我想在标签上的任意位置单击以开始播放。 I have tried putting "display: block;" 我试过把“ display:block;” in my css code in the label definition but this did not work. 在标签定义的CSS代码中,但这没有用。
2. When I press "near the label" of the second audio element it plays the audio of the first audio element. 2.当我按下第二个音频元素的“标签附近”时,它将播放第一个音频元素的音频。 I'm wondering how I can edit the javascript code so that it can play multiple audio files. 我想知道如何编辑javascript代码,以便它可以播放多个音频文件。 Thanks for the help. 谢谢您的帮助。 Here is my html code: 这是我的html代码:

<ul id="audio_list">

<li>


    <div class="audio_controls gradient_dblue">
        <div class=circle></div>
        <div class="switch play_button">
            <audio class="audio-player"> 
                <source src="music/electronic beat-monksee.mp3" type="audio/mpeg" />
                        <source src="music/electronic beat-monksee.mp3" type="audio/mpeg" />
                        Your browser does not support HTML5 audio.
                    </audio>

            <input type="checkbox">
            <label class="play-bt"><i class='icon-play fade'></i><i class='icon-stop fade'></i></label>

        </div>

    </div>
    <div class="audio_description">Electro sounds</br><div class="artist">Sarah monks</div></div>

</li>



<li>
    <div class="audio_controls gradient_dblue">
        <div class=circle></div>
        <div class="switch play_button">
            <audio class="audio-player"> 
                <source src="music/dubstep.mp3" type="audio/mpeg" />
                        <source src="music/dubstep.mp3" type="audio/mpeg" />
                        Your browser does not support HTML5 audio.
                    </audio>

            <input type="checkbox">
            <label class="play-bt"><i class='icon-play fade'></i><i class='icon-stop fade'></i></label>

        </div>

    </div>
    <div class="audio_description">Dubstep Beat</br><div class="artist">Sarah monks</div></div>


</li>



</ul>

here is my javascript code: 这是我的JavaScript代码:

$(document).ready(function(){
    $(".play-bt").click(function(){
        $(".audio-player")[0].play();
        $("#message").text("Music started");
    })

    $(".pause-bt").click(function(){
        $(".audio-player")[0].pause();
        $("#message").text("Music paused");
    })

    $(".stop-bt").click(function(){
        $(".audio-player")[0].pause();
        $(".audio-player")[0].currentTime = 0;
        $("#message").text("Music Stopped");
    })
})

here is my html code simplified a bit: 这是我的html代码简化了一点:

<ul id="audio_list">

<li>


    <div class="audio_controls">
        <div class="switch play_button">
            <audio class="audio-player"> 
                <source src="music/electronic beat-monksee.mp3" type="audio/mpeg" />
                    </audio>

            <input type="checkbox">
            <label class="play-bt"><i class='icon-play fade'></i><i class='icon-stop fade'></i></label>

        </div>

    </div>
    <div class="audio_description">Electro sounds</div>

</li>



<li>
    <div class="audio_controls">
        <div class="switch play_button">
            <audio class="audio-player"> 
                <source src="music/dubstep.mp3" type="audio/mpeg" />
                    </audio>

            <input type="checkbox">
            <label class="play-bt"><i class='icon-play fade'></i><i class='icon-stop fade'></i></label>

        </div>

    </div>
    <div class="audio_description">Dubstep Beat</div>   

</li>

</ul>

Edit: This is my while loop which loops through all of the rows of my database 编辑:这是我的while循环,遍历数据库的所有行

<?php
$host = "localhost"; 
$user = ""; 
$pass = ""; 
$db = ""; 

$con=mysqli_connect($host,$user,$pass,$db);
        // Check connection
        if (mysqli_connect_errno())
            {
            echo "Failed to connect to MySQL: " . mysqli_connect_error();
            }

            $result = mysqli_query($con,"SELECT * FROM products");
            if (!$result) {
                printf("Error: %s\n", mysqli_error($con));
                exit();
            }
            echo "<ul id='audio_list'>";

        while($row = mysqli_fetch_array($result))
        {
            ?>
        <li>
        <div class='audio_controls_area'>
            <div class='play_button'>

                <input class="controler_btn click_play" type='checkbox'>
                <label class='play-bt'><i class='icon-play fade'></i><i class='icon-stop fade'></i></label>
                <audio class='audio-player'> 
                    <source src=<?php echo $row['Productmp3']; ?> type='audio/mpeg' />
                            <source src=<?php echo $row['Productmp3']; ?> type='audio/ogg' />
                    <object type='audio/x-mpeg' width='300px' height='45px' data=<?php echo $row['Productmp3']; ?> >
                        <param name='src' value=<?php echo $row['Productmp3']; ?> />
                        <param name='autoplay' value='false' />
                        <param name='autostart' value='false' />
                    </object>
                        </audio>

            </div>

        </div>
        <div class='audio_description'><?php echo $row['ProductName']; ?>
        <br>
        <div class="message"></div>
        <div class="artist"><?php echo $row['ProductArtist']; ?></div>
        </div>

        </li>
         <?php
        }
        echo "</ul>";
        mysqli_close($con);
        ?>

I got help the next day after I posted this with jquery code that would allow only one song play at a time and that could play and stop a song as required. 我在用jQuery代码发布此代码后的第二天获得了帮助,该代码一次只允许播放一首歌曲,并且可以根据需要播放和停止一首歌曲。

$(document).ready(function(){
    function stop_all (ele) {
        console.log(ele + "in funct");
        //console.log(ele.parent().parent().parent().siblings().find(".audio-player").length);
        var list = ele.parent().parent().parent().siblings().find(".audio-player");
        console.log(list.length);
        list.each(function(){
            $(this).siblings(".controler_btn").prop('checked', false).removeClass("click_stop").addClass("click_play");
            //alert($(this).siblings(".controler_btn"));
            console.log("loop");
            $(this)[0].pause();
            $(this)[0].currentTime = 0;
        });
    }
        $(".controler_btn").click(function(){
            if ($(this).hasClass("click_play")) {
                stop_all($(this));
                console.log($(this).parent().parent().parent().siblings().find(".audio-player"))
                console.log("playing");
                $(this).removeClass("click_play").addClass("click_stop");
                $(this).siblings(".audio-player")[0].play();
                $(this).parent().parent().siblings(".audio_description ").find(".message").show().html("Music started").hide(3000);
                //$(".audio-player")[0].play();
                //$("#message").text("Music started");
            }
            else if ($(this).hasClass("click_stop")) {
                console.log("stopped");
                $(this).removeClass("click_stop").addClass("click_play");
                $(this).siblings(".audio-player")[0].pause();
                $(this).siblings(".audio-player")[0].currentTime = 0;
                //$(".audio-player")[0].pause();
                //$(".audio-player")[0].currentTime = 0;
                $(this).siblings(".message").show().text("Music Stopped").hide(3000);
                //$("#message").text("Music Stopped");
            }

        })
    })

Thanks to @kuroi neko for your advice. 感谢@kuroi neko的建议。 I see what you mean about the resources. 我明白您对资源的意思。 This code works great but I would like to edit it as you said with the for loops and the id on the audio players as the site is really for mobile so I would like to make it more practical. 这段代码很好用,但是我想像您所说的那样使用for循环和音频播放器上的id对其进行编辑,因为该站点确实是移动设备,所以我想使其更加实用。 I'm wondering in the php code would I need to put the for loop inside the while loop or have only a for loop instead? 我想知道在php代码中是否需要将for循环放入while循环内,或者只使用for循环? Thanks 谢谢

This is no JavaScript. 这不是JavaScript。 This is the dreaded JQuery, that allows you to write inefficient and obfuscated code that takes hours to debug :). 这就是可怕的JQuery,它使您可以编写效率低下且混淆不清的代码,这些代码需要花费数小时才能调试:)。

Seriously, querying all audio player divs each time you move a matchstick is terribly inefficient. 严重的是,每次移动火柴棍时查询所有音频播放器的div效率都非常低。 In that case it does not matter because it's just a user interface, but doing that for each paragraph of your document would make your code crawl. 在那种情况下,这并不重要,因为它只是一个用户界面,但是对文档的每个段落进行操作都会使您的代码爬行。
(taking a French leave before being skinned alive by the JQuery crowd...) (在被JQuery人群剥皮之前请法国休假...)

problem 1 问题1

What you ask JQuery to do is put a click handler on your 3rd div. 您要求JQuery进行的操作是在第3个div上放置一个点击处理程序。 It does just that, so you can only generate a click event if you manage to put your mouse cursor on the said div. 它就是这样做的,因此,仅当您将鼠标光标放在该div上时,您才可以生成click事件。

Without any stylesheet, your div happens to have a height of 0 pixels, which makes it hard to locate on the screen. 没有任何样式表,您的div恰好具有0像素的高度,这使其很难在屏幕上定位。 I suppose you did uses some CSS, but my guess is, it was not good enough to make your play button stand out. 我想您确实使用了一些CSS,但是我想是,它还不足以让您的播放按钮脱颖而出。

I did run your code with the following CSS : 我确实使用以下CSS运行您的代码:

.play-bt { display:inline-block; background:red; width: 30px; height:30px;}

and the play button acquired a height and became a responsive big red square :) 播放按钮变高了,变成了一个反应迅速的大红色方块:)

problem 2 问题2

You hard-coded your click handler to use the 1st div that happens to have a play-bt CSS class, so wherever you click, the 1st song will be played: 您已对点击处理程序进行了硬编码,以使用恰好具有play-bt CSS类的第一个div,因此无论您单击何处,都会播放第一首歌:

$(".audio-player")[ 0 ].play(); // this "0" selects the 1st audio player $(".audio-player")[ 0 ].play(); // this "0" selects the 1st audio player ].play(); // this "0" selects the 1st audio player

To avoid that, you have to associate each play/stop/pause button with the appropriate audio div. 为避免这种情况,您必须将每个播放/停止/暂停按钮与相应的音频div关联。


Edited after Sarah's remarks 在莎拉的讲话后编辑

the famous button 著名的按钮

It appears you styled the checkbox (very nicely, by the way), so I assume the checkbox is the intended button. 看来您为复选框设置了样式(顺便说一句,很好),所以我认为该复选框预期的按钮。 But your JQuery goo code is aiming at the div just next to it :) 但是您的JQuery goo代码针对的是它旁边的div :)
Move the bn-play CSS class from this div to your checkbox and Bob should be your uncle. bn-play CSS类从该div移到您的复选框,Bob应该是您的叔叔。

pairing buttons with the proper audio player 与正确的音频播放器配对按钮

There are many possibilities to achieve this. 有许多实现此目的的可能性。

Since you will use PHP to generate the HTML, I would suggets attributing a unique ID to each of your audio div, and use it to query the proper audio from within your event handlers. 由于您将使用PHP生成HTML,因此建议您为每个音频div分配一个唯一的ID,并使用它从事件处理程序中查询正确的音频。

Very schematic PHP code: 非常简单的PHP代码:

$audio_id = 0; // unique ID for each mp3 player

// part of the HTML generation
foreach ($songs as $song)
{
    echo "<audio id='audio_" . $audio_id . "'>"; // generate a unique ID
    $audio_id++;                                 // for each audio block
}

Even more schematic JQuery g... code 甚至更多的JQuery g原理图代码

for (var i = 0 ; i != number_of_audio_files_on_the_page ; i++)
{
    $(".play-bt").click(function(){
        $("#audio_" + i).play();         // reference the audio_xxx unique id
        $("#message").text("Music started");
    })

   // same trick for other buttons
}

Note that this code will not work out of the box: you will need a closure on the loop index. 请注意,此代码无法立即使用:您将需要在循环索引上进行关闭。 But this another story. 但这是另一个故事。

more on resources consumption 更多关于资源消耗

Having a different audio player for each song is both wasteful and impractical, IMHO. 恕我直言,为每首歌曲使用不同的音频播放器既浪费又不切实际。

It is wasteful because (especially if you allow auto-buffering), each MP3 file will be downloaded in parallel, even if the user never plays it. 这很浪费,因为(特别是如果您允许自动缓冲),即使用户从未播放过每个MP3文件,也将并行下载。 The browser will permanently allocate a few megabytes of MP3 data for each song on the page. 浏览器将为页面上的每首歌曲永久分配几MB的MP3数据。

As for practicality, imagine what will happen if the user starts playing a song and then clicks another "play" button... 关于实用性,请想象一下,如果用户开始播放一首歌曲,然后单击另一个“播放”按钮,将会发生什么...
Unless real-time remixes are a lead feature of your site, you will want to prevent the user from inadvertently playing more than one song at a time :). 除非实时混音是您网站的主要功能,否则您将希望防止用户无意间一次播放多首歌曲:)。

To kill the two birds, a possible single stone would be to create a single audio player, and change the source according to the last "play" button pressed. 为了杀死两只鸟,可能的办法是创建一个音频播放器,并根据最后按下的“播放”按钮更改源。

This could even lead to a redesign of your interface, since there would be no need for a pause or stop button next to each song. 这甚至可能会导致界面的重新设计,因为不需要在每首歌曲旁边添加暂停或停止按钮。

You could imagine a "select" button next to each song (that would also stop the current song and start the newly selected one), and another control pannel in the header or footer of the page with more sophisticated controls acting on the current song (a seek bar for instance). 您可以想象每首歌曲旁边有一个“选择”按钮(这也将停止当前歌曲并开始新选择的歌曲),并在页面的页眉或页脚中显示另一个控件面板,其中更复杂的控件作用于当前歌曲(例如搜索栏)。

a little update 一点更新

This is a true eyesore that can turn into a headache any time: 这是真正的烦恼,任何时候都可能引起头痛:

var list = ele.parent().parent().parent().siblings().find(".audio-player");

One of the many drawbacks of JQuery is that it makes much too easy to navigate between DOM elements. JQuery的许多缺点之一是,它太容易在DOM元素之间导航。 It means your code tends to become dependent on the structure of the document. 这意味着您的代码倾向于依赖于文档的结构。

Functionnally, you don't care where the audio players and all the buttons are located. 功能上,您无需担心音频播放器和所有按钮的位置。 You should only access them by class names or IDs. 您只能按类名称或ID访问它们。

Using this code, you must know that the audio players are the fore-fore-fore-fathers of whatever element you were playing with at the time you decided to access them, the play button is the second cousin of the seekbar, etc. 使用此代码,您必须知道音频播放器是您决定访问它们时正在使用的任何元素的先行者,播放按钮是seekbar的第二堂兄,等等。
It means you will have to tweak your code each time you want to change the page layout. 这意味着您每次要更改页面布局时都必须调整代码。 Very impractical, IMHO. 非常不切实际,恕我直言。

My advice would be to write a function that handles start/stop/pause for a given audio player, and then call that function at the appropriate time: 我的建议是编写一个处理给定音频播放器开始/停止/暂停的函数,然后在适当的时间调用该函数:

  • on the current song to play it, and on the others to stop them 在当前歌曲上播放,在其他歌曲上停止播放
  • on the current song to pause or stop it. 在当前歌曲上暂停或停止播放。

So I cannot really answer your question about for/while loops. 因此,我无法真正回答您有关for / while循环的问题。 I think a more global code refactoring would be a better investment to keep your design light and evolutive. 我认为,更具全局性的代码重构将是使您的设计更轻巧和不断发展的更好的投资。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM