我有以下div,并且在其中是输入文本。 div有一个弹出框,我希望在输入文本处于焦点时显示它。如果输入文本不清晰,我希望隐藏弹出框。我目前正在尝试使用以下代码进行操作:

HTML:

<div id="divParent" bs-popover
    data-trigger="focus click"
    data-auto-close="1"
    data-placement="bottom"
    class="pswd-popover"
    data-template-url="people/user/user-profile/templates/password-requirements.html">
    <rp-form-input-text
        rp-model="page.userData.password"
        config="page.formConfig.password">
    </rp-form-input-text>
</div>

模型:
model.password = inputTextConfig({
    id: "password",
    fieldName: "password",
    dataType: "password",
    required: false,
    maxLength: 24,
    modelOptions: {
        allowInvalid: true,
    },
    onFocus: model.getMethod("showPopover")
});

Controller :
vm.showPopover = function () {
    var focus = true;

    $(window).keyup(function (e) {
        var code = (e.keyCode ? e.keyCode : e.which);
        if (code == 9 && focus) {
            $timeout(function() {
                angular.element('#divParent').trigger('click');
            }, 100);
            focus = false;
        }
    });

};

我遇到的问题是我只希望通过标签触发onfocus函数。因为单击div会自动触发弹出窗口的显示。这就是为什么我具有keyup函数以便检测div是否通过TAB单击或访问的原因。另一个问题是,我仅通过触发div的onclick来显示和隐藏弹出窗口。如何显示和隐藏父div的弹出框?

最佳答案

我确实实现了这一点-仅在选项卡上触发(而不是在单击字段时触发),但我怀疑您想同时包括两者,因此您也可以在下面找到该情况的代码。

您可以使用$popover服务对触发它进行更精确的控制。

var app = angular.module('app', ['ngAnimate', 'ngSanitize', 'mgcrea.ngStrap']);

app.controller('MainCtrl', function($scope, $popover) {

  // sometimes we don't want to trigger code to show the Popover
  $scope.suspendPopoverAction = false;

  $scope.popover = {
    title: 'HEY',
    content: 'This was triggered by tabbing.'
  };

  var asAServiceOptions = {
    title: $scope.popover.title,
    content: $scope.popover.content,
    trigger: 'manual',
    placement: 'bottom',
    autoClose: true,
    onBeforeShow: function() {
      $scope.activeElement = document.activeElement; // record element with focus
      $scope.suspendPopoverAction = true; // don't trigger blur code
    },
    onShow: function() {
      if ($scope.activeElement) $scope.activeElement.focus(); // restore focus
      $scope.suspendPopoverAction = false; // popup is showing, and focus is back to input, so now safe for blur code
    }
  };

  var myPopover = $popover(angular.element(document.querySelector('#divParent')), asAServiceOptions);

  $scope.inputHasFocus = function() {
    if (!$scope.suspendPopoverAction) {
      myPopover.$promise.then(myPopover.show);
    } else {
      $scope.suspendPopoverAction = false;
    }
  };

  $scope.inputLostFocus = function() {
    if (!$scope.suspendPopoverAction) {
      myPopover.$promise.then(myPopover.hide);
    }
  };

  $scope.inputClicked = function(event) {
    $scope.suspendPopoverAction = true; // prevent popover from showing on click

    // NB: If you want to allow mouse clicks also:
    // 1) use ng-click instead of ng-mousedown in the <input>
    // 2) remove "$scope.suspendPopoverAction = true;" line and replace with:
    //      event.stopPropagation();
    // Doing the above prevents the click triggering the "autoClose: true" option, resulting in flickering of the Popover
  };
});
body {
  padding: 5px !important;
}

.pswd-popover {
  background-color: orange;
  padding: 10px;
  margin: 10px;
}

.myheading {
  margin-bottom: 15px;
}
<!DOCTYPE html>
<html ng-app="app">

<head>
  <meta charset="utf-8" />
  <link rel="stylesheet" href="//cdn.jsdelivr.net/fontawesome/4.5.0/css/font-awesome.css">
  <link rel="stylesheet" href="//cdn.jsdelivr.net/bootstrap/3.3.6/css/bootstrap.min.css">
  <link rel="stylesheet" href="//mgcrea.github.io/angular-strap/styles/libs.min.css">
  <link rel="stylesheet" href="//mgcrea.github.io/angular-strap/styles/docs.min.css">
  <script src="//cdn.jsdelivr.net/angularjs/1.5.5/angular.min.js" data-semver="1.5.5"></script>
  <script src="//cdn.jsdelivr.net/angularjs/1.5.5/angular-animate.min.js" data-semver="1.5.5"></script>
  <script src="//cdn.jsdelivr.net/angularjs/1.5.5/angular-sanitize.min.js" data-semver="1.5.5"></script>
  <script src="//mgcrea.github.io/angular-strap/dist/angular-strap.js" data-semver="v2.3.8"></script>
  <script src="//mgcrea.github.io/angular-strap/dist/angular-strap.tpl.js" data-semver="v2.3.8"></script>
  <script src="//mgcrea.github.io/angular-strap/docs/angular-strap.docs.tpl.js" data-semver="v2.3.8"></script>
</head>

<body ng-controller="MainCtrl">

  <h4 class = "myheading">Trigger Popover on Tabbing in Password field only</h4>
  An input for testing Tab:
  <input type="text">

  <div id="divParent" class="pswd-popover">
    Password:
    <input type="text" ng-focus="inputHasFocus()" ng-blur="inputLostFocus()" ng-mousedown="inputClicked($event)">
    <button>Some Button</button>
  </div>

  Another input for testing Tab:
  <input type="text">

</body>

</html>


要在选择或单击密码字段时显示弹出框:

var app = angular.module('app', ['ngAnimate', 'ngSanitize', 'mgcrea.ngStrap']);

app.controller('MainCtrl', function($scope, $popover) {

  // sometimes we don't want to trigger code to show the Popover
  $scope.suspendPopoverAction = false;

  $scope.popover = {
    title: 'HEY',
    content: 'Triggered by tabbing OR clicking.'
  };

  var asAServiceOptions = {
    title: $scope.popover.title,
    content: $scope.popover.content,
    trigger: 'manual',
    placement: 'bottom',
    autoClose: true,
    onBeforeShow: function() {
      $scope.activeElement = document.activeElement; // record element with focus
      $scope.suspendPopoverAction = true; // don't trigger blur code
    },
    onShow: function() {
      if ($scope.activeElement) $scope.activeElement.focus(); // restore focus
      $scope.suspendPopoverAction = false; // popup is showing, and focus is back to input, so now safe for blur code
    }
  };

  var myPopover = $popover(angular.element(document.querySelector('#divParent')), asAServiceOptions);

  $scope.inputHasFocus = function() {
    if (!$scope.suspendPopoverAction) {
      myPopover.$promise.then(myPopover.show);
    } else {
      $scope.suspendPopoverAction = false;
    }
  };

  $scope.inputLostFocus = function() {
    if (!$scope.suspendPopoverAction) {
      myPopover.$promise.then(myPopover.hide);
    }
  };

  $scope.inputClicked = function(event) {
    // using the below code prevents the click triggering the "autoClose: true" option resulting in flickering
    event.stopPropagation();
  };
});
body {
  padding: 5px !important;
}

.pswd-popover {
  background-color: orange;
  padding: 10px;
  margin: 10px;
}

.myheading {
  margin-bottom: 15px;
}
<!DOCTYPE html>
<html ng-app="app">

<head>
  <meta charset="utf-8" />
  <link rel="stylesheet" href="//cdn.jsdelivr.net/fontawesome/4.5.0/css/font-awesome.css">
  <link rel="stylesheet" href="//cdn.jsdelivr.net/bootstrap/3.3.6/css/bootstrap.min.css">
  <link rel="stylesheet" href="//mgcrea.github.io/angular-strap/styles/libs.min.css">
  <link rel="stylesheet" href="//mgcrea.github.io/angular-strap/styles/docs.min.css">
  <script src="//cdn.jsdelivr.net/angularjs/1.5.5/angular.min.js" data-semver="1.5.5"></script>
  <script src="//cdn.jsdelivr.net/angularjs/1.5.5/angular-animate.min.js" data-semver="1.5.5"></script>
  <script src="//cdn.jsdelivr.net/angularjs/1.5.5/angular-sanitize.min.js" data-semver="1.5.5"></script>
  <script src="//mgcrea.github.io/angular-strap/dist/angular-strap.js" data-semver="v2.3.8"></script>
  <script src="//mgcrea.github.io/angular-strap/dist/angular-strap.tpl.js" data-semver="v2.3.8"></script>
  <script src="//mgcrea.github.io/angular-strap/docs/angular-strap.docs.tpl.js" data-semver="v2.3.8"></script>
</head>

<body ng-controller="MainCtrl">

  <h4 class = "myheading">Trigger Popover on Tabbing or Clicking in Password field</h4>
  An input for testing Tab:
  <input type="text">

  <div id="divParent" class="pswd-popover">
    Password:
    <input type="text" ng-focus="inputHasFocus()" ng-blur="inputLostFocus()" ng-click="inputClicked($event)">
    <button>Some Button</button>
  </div>

  Another input for testing Tab:
  <input type="text">

</body>

</html>


还要注意HTML中的细微变化。此版本使用<input ng-click="",而仅制表符的代码使用<input ng-mousedown=""。此更改可防止与auto-close: true关联的闪烁。

08-25 16:23
查看更多