Add functional popover directive

This commit is contained in:
gconsidine 2017-05-08 16:26:01 -04:00
parent b8d87028c9
commit 255665b98e
9 changed files with 118 additions and 32 deletions

View File

@ -1,20 +1,29 @@
let eventService;
let pathService;
function link (scope, el, attrs, form) {
form.use(scope, el);
let apply = eventService.listenWith(scope);
let input = el.find('input')[0];
let select = el.find('select')[0];
input.addEventListener('focus', () => select.focus());
select.addEventListener('focus', () => input.classList.add('at-Input--focus'));
select.addEventListener('mousedown', () => scope.open = !scope.open);
select.addEventListener('change', () => scope.open = false );
select.addEventListener('blur', () => {
input.classList.remove('at-Input--focus')
input.addEventListener('focus', apply(select.focus));
select.addEventListener('mousedown', apply(() => scope.open = !scope.open));
select.addEventListener('change', () => apply(() => scope.open = false));
select.addEventListener('focus', apply(() => input.classList.add('at-Input--focus')));
select.addEventListener('blur', apply(() => {
input.classList.remove('at-Input--focus');
scope.open = scope.open && false;
});
}));
}
function atInputSelect (pathService) {
function atInputSelect (_eventService_, _pathService_) {
eventService = _eventService_;
pathService = _pathService_;
return {
restrict: 'E',
transclude: true,
@ -29,6 +38,9 @@ function atInputSelect (pathService) {
};
}
atInputSelect.$inject = ['PathService'];
atInputSelect.$inject = [
'EventService',
'PathService'
];
export default atInputSelect;

View File

@ -1,10 +1,10 @@
<div class="row">
<div class="col-xs-11">
<div class="col-xs-10">
<h3 class="at-Panel-headingTitle">
{{ config.text }}
</h3>
</div>
<div class="col-xs-1">
<div class="col-xs-2">
<div class="at-Panel-dismiss">
<i class="fa fa-times-circle fa-lg" ng-click="dismiss()"></i>
</div>

View File

@ -6,12 +6,25 @@
}
.at-Popover-container {
visibility: hidden;
opacity: 0;
color: @at-white;
background-color: @at-gray-dark;
max-width: @at-popover-width;
height: 100%;
padding: @at-padding-md;
height: auto;
position: fixed;
top: 0px;
left: 5px;
z-index: 2000;
margin: 0 0 0 @at-margin-md;
border-radius: @at-border-radius-md;
box-shadow: 0 5px 10px rgba(0,0,0, 0.2);
transition: opacity .15s linear;
}
.at-Popover-arrow {
color: @at-gray-dark;
position: fixed;
z-index: 1999;
padding: 0;
margin: -@at-margin-xxs 0 0 0;
}

View File

@ -1,21 +1,58 @@
let pathService;
function link (scope, el, attr) {
scope.show = false;
let icon = el[0];
let popover = icon.getElementsByClassName('at-Popover-container')[0];
el.on('click', createPopover.bind(null, scope));
el.on('click', createDisplayListener(icon, popover));
}
function createPopover (scope, event) {
scope.show = !scope.show;
function createDisplayListener (icon, popover) {
return event => {
let arrow = popover.getElementsByClassName('at-Popover-arrow')[0];
let w = window.outerWidth;
let h = window.outerHeight;
let x = event.clientX;
let y = event.clientY;
let iPos = icon.getBoundingClientRect();
let pPos = popover.getBoundingClientRect();
console.log(event);
let wHeight = window.clientHeight;
let pHeight = pPos.height;
let cx = Math.floor(iPos.left + (iPos.width / 2));
let cy = Math.floor(iPos.top + (iPos.height / 2));
if (cy < (pHeight / 2)) {
popover.style.top = '10px';
} else {
popover.style.top = (cy - pHeight / 2) + 'px';
}
popover.style.left = cx + 'px';
arrow.style.top = iPos.top + 'px';
arrow.style.left = iPos.left + 20 + 'px';
popover.style.visibility = 'visible';
popover.style.opacity = 1;
let dismissListener = createDismissListener(popover);
window.addEventListener('mousedown', dismissListener);
window.addEventListener('resize', dismissListener);
};
}
function atPopover (pathService) {
function createDismissListener (popover) {
return function dismissListener () {
popover.style.visibility = 'hidden';
popover.style.opacity = 0;
window.removeEventListener('mousedown', dismissListener);
};
}
function atPopover (_pathService_) {
pathService = _pathService_;
return {
restrict: 'E',
replace: true,
@ -28,6 +65,8 @@ function atPopover (pathService) {
};
}
atPopover.$inject = ['PathService'];
atPopover.$inject = [
'PathService'
];
export default atPopover;

View File

@ -1,12 +1,11 @@
<div class="at-Popover">
<span ng-if="config" class="at-Popover-icon">
<div ng-show="config" class="at-Popover">
<span class="at-Popover-icon">
<i class="fa fa-question-circle"></i>
</span>
<div ng-show="show" class="at-Popover-container">
<div class="at-Popover-container">
<div class="at-Popover-arrow">
<i class="fa fa-caret-left fa-2x"></i>
</div>
<div class="at-Popover-content">Bacon ipsum dolor amet cow shank tenderloin bresaola chicken picanha leberkas jerky shankle. Tri-tip t-bone bacon, flank jerky porchetta cow. Landjaeger ham tenderloin flank pork chop. Fatback landjaeger short ribs andouille meatloaf shank tri-tip. Flank chicken ham jerky leberkas.
</div>
<div class="at-Popover-content">{{ config.text }}</div>
</div>
</div>

View File

@ -0,0 +1,16 @@
function listenWith (scope) {
return fn => apply(scope, fn);
}
function apply (scope, fn) {
return () => scope.$apply(fn);
}
function EventService () {
return {
listenWith,
apply
};
}
export default EventService;

View File

@ -1,5 +1,7 @@
import EventService from './event.service';
import PathService from './path.service';
angular
.module('at.lib', [])
.factory('EventService', EventService)
.factory('PathService', PathService);

View File

@ -5,7 +5,9 @@ function AddCredentialsController (credentialType) {
label: {
text: 'Name',
required: true,
popover: {}
popover: {
text: 'a, b, c'
}
}
};
@ -23,7 +25,9 @@ function AddCredentialsController (credentialType) {
label: {
text: 'Type',
required: true,
popover: {}
popover: {
text: 'x, y, z'
}
},
placeholder: 'Select a Type',
text: 'kind',

View File

@ -25,6 +25,7 @@
@at-padding-sm: 10px;
@at-padding-md: 20px;
@at-margin-xxs: 3px;
@at-margin-xs: 4px;
@at-margin-sm: 10px;
@at-margin-md: 20px;