我可以使用Angular变量作为音频标签的来源吗?

时间:2014-05-14 15:47:36

标签: javascript angularjs audio angularjs-directive angularjs-ng-repeat

我正在尝试执行以下操作:

<div ng-repeat="audio in event.audios">
    <audio ng-src="/data/media/{{audio}}" controls></audio>
</div>

但是当我加载视图时,{{audio}}变量不会被解析,而是按原样硬编码到源中。但是,例如,如果我将相同的变量放在音频标签之外,它会正确呈现音频文件的名称。我尝试过使用src和ng-src都无济于事。

有没有办法让变量在音频标签中工作?

提前致谢。

4 个答案:

答案 0 :(得分:7)

我不是所有 熟悉ngSrc指令,除了在图像上使用它之外,但它可能需要在源代码中的某个地方使用img标记。

<击>

试试这个:

<div ng-repeat="audio in event.audios">
    <audio ng-attr-src="/data/media/{{audio}}" controls></audio>
</div>

ng-attr-指令可用于任何角度没有特定角色的属性。您可以在this page上详细了解相关信息。

更新,我错了。

我创建了一个jsfiddle,发现了正在发生的实际错误。

你从sce服务中收到错误。请参阅SO问题here

解决方案是使用$sce.trustAsResourceUrl()

示例:

angular.module('AudioTest', [])
.controller('AudioTestCtrl', function($scope, $sce) {
    $scope.event = { 'audios': [
        $sce.trustAsResourceUrl('/data/media/test1'),
        $sce.trustAsResourceUrl('/data/media/test2')
    ]};
});

Here's the fiddle

更新#2

如果您不希望将url设置为硬编码或在从服务器获得响应后进行循环,则可以使用自定义过滤器来完成您要查找的内容。此方法不使用插值,这是抛出错误的地方。

JS:

angular.module('AudioTest', [])
.filter('trustedAudioUrl', function($sce) {
    return function(path, audioFile) {
        return $sce.trustAsResourceUrl(path + audioFile);
    };
})
.controller('AudioTestCtrl', function($scope) {
    $scope.event = { 'audios': ['test1', 'test2']};
});

HTML:

<div ng-app="AudioTest">
    <div ng-controller="AudioTestCtrl">
        <div ng-repeat="audio in event.audios">
            <audio ng-src="/data/media/ | trustedAudioUrl:audio)" controls></audio>
        </div>
    </div>
</div>

new fiddle

答案 1 :(得分:6)

好的,感谢theJoeBiz的输入和一些思考我通过制定指令解决了这个问题,这里是代码:

app.directive('audios', function($sce) {
  return {
    restrict: 'A',
    scope: { code:'=' },
    replace: true,
    template: '<audio ng-src="{{url}}" controls></audio>',
    link: function (scope) {
        scope.$watch('code', function (newVal, oldVal) {
           if (newVal !== undefined) {
               scope.url = $sce.trustAsResourceUrl("/data/media/" + newVal);
           }
        });
    }
  };
});

然后在模板上我就这样使用它:

<div ng-repeat="audio in event.audios">
    <div audios code="audio"></div>
</div>

现在一切正常。

答案 2 :(得分:3)

嘿FWIW我发现这个页面正在为我的音频标签寻找模板URL的解决方案。但是我使用多个源代码标签来支持跨浏览器:

<audio id="myAudioTag">
  <source ng-src="{{sceSoundUrlMp3}}">
  <source ng-src="{{sceSoundUrlOgg}}">
</audio>

首先,我通过白名单* .ogg,* .mp3解决了SCE问题:(保持'自我',否则你的未来请求会失败)

.config(function($sceDelegateProvider) {
  $sceDelegateProvider.resourceUrlWhitelist([
    "self",
    /(mp3|ogg)$/,
  ]);
})

这已停止提供SCE错误,但Firefox报告“没有来源”,并且没有注意到src标记已添加角度。

最后一步是在信任并设置$scope.sceSoundUrlMp3之后调用元素上的加载:$('#myAudioTag')[0].load()

答案 3 :(得分:0)

我使用了$sce.trustAsResourceUrl("/data/media/" + newVal)但它没有用。似乎对我有用的是放document.getElementById('player').src = {{url}} 在控制器中

希望能帮助别人