Skip to content

Commit

Permalink
Merge pull request #222 from microsoftgraph/nivogt/card-window-bounds
Browse files Browse the repository at this point in the history
Fixed issue where flyouts render outside of window bounds
  • Loading branch information
vogtn authored and shweaver-MSFT committed Jun 8, 2020
1 parent 77e0e30 commit 89afe03
Show file tree
Hide file tree
Showing 7 changed files with 313 additions and 165 deletions.
22 changes: 20 additions & 2 deletions packages/mgt/src/components/baseComponent.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
* -------------------------------------------------------------------------------------------
*/

import { LitElement } from 'lit-element';
import { LitElement, PropertyValues } from 'lit-element';
/**
* BaseComponent extends LitElement including ShadowRoot toggle and fireCustomEvent features
*
Expand Down Expand Up @@ -45,7 +45,7 @@ export abstract class MgtBaseComponent extends LitElement {
}

/**
* Recieve ShadowRoot Disabled value
* Receive ShadowRoot Disabled value
*
* @returns boolean _useShadowRoot value
* @memberof MgtBaseComponent
Expand Down Expand Up @@ -81,4 +81,22 @@ export abstract class MgtBaseComponent extends LitElement {
protected createRenderRoot() {
return this.isShadowRootDisabled() ? this : super.createRenderRoot();
}

/**
* Invoked whenever the element is updated. Implement to perform
* post-updating tasks via DOM APIs, for example, focusing an element.
*
* Setting properties inside this method will trigger the element to update
* again after this update cycle completes.
*
* * @param changedProperties Map of changed properties with old values
*/
protected updated(changedProperties: PropertyValues) {
super.updated(changedProperties);
const event = new CustomEvent('updated', {
bubbles: true,
cancelable: true
});
this.dispatchEvent(event);
}
}
16 changes: 1 addition & 15 deletions packages/mgt/src/components/mgt-person/mgt-person.scss
Original file line number Diff line number Diff line change
Expand Up @@ -137,20 +137,6 @@ mgt-person .user-email {
-ms-grid-row: 2;
}

.root .flyout {
display: none;
position: absolute;
z-index: 1;
opacity: 0;
transition-property: opacity;
transition-duration: 0.1s;
.flyout {
padding: 8px;
}

.root .flyout.visible {
display: inline-block;
opacity: 1;
&.openLeft {
right: 0;
}
}
103 changes: 44 additions & 59 deletions packages/mgt/src/components/mgt-person/mgt-person.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,13 +6,15 @@
*/

import * as MicrosoftGraph from '@microsoft/microsoft-graph-types';
import { customElement, html, property, PropertyValues } from 'lit-element';
import { customElement, html, property, PropertyValues, TemplateResult } from 'lit-element';
import { classMap } from 'lit-html/directives/class-map';
import { styleMap } from 'lit-html/directives/style-map';
import { Providers } from '../../Providers';
import { ProviderState } from '../../providers/IProvider';
import '../../styles/fabric-icon-font';
import { getEmailFromGraphEntity } from '../../utils/GraphHelpers';
import { MgtPersonCard } from '../mgt-person-card/mgt-person-card';
import '../sub-components/mgt-flyout/mgt-flyout';
import { MgtTemplatedComponent } from '../templatedComponent';
import { PersonCardInteraction } from './../PersonCardInteraction';
import { styles } from './mgt-person-css';
Expand Down Expand Up @@ -115,8 +117,8 @@ export class MgtPerson extends MgtTemplatedComponent {
})
public personCardInteraction: PersonCardInteraction = PersonCardInteraction.none;

@property({ attribute: false }) private _isPersonCardVisible: boolean = false;
@property({ attribute: false }) private _personCardShouldRender: boolean = false;
@property({ attribute: false }) private isPersonCardVisible: boolean = false;
@property({ attribute: false }) private personCardShouldRender: boolean = false;

private _mouseLeaveTimeout;
private _mouseEnterTimeout;
Expand Down Expand Up @@ -172,11 +174,11 @@ export class MgtPerson extends MgtTemplatedComponent {
return html`
<div
class="root"
@mouseenter=${this._handleMouseEnter}
@mouseleave=${this._handleMouseLeave}
@click=${this._handleMouseClick}
@mouseenter=${this.handleMouseEnter}
@mouseleave=${this.handleMouseLeave}
@click=${this.handleMouseClick}
>
${person} ${this.renderPersonCard()}
${this.renderFlyout(person)}
</div>
`;
}
Expand Down Expand Up @@ -284,40 +286,41 @@ export class MgtPerson extends MgtTemplatedComponent {
this.requestUpdate();
}

private _handleMouseClick() {
if (this.personCardInteraction === PersonCardInteraction.click && !this._isPersonCardVisible) {
this._showPersonCard();
private handleMouseClick() {
if (this.personCardInteraction === PersonCardInteraction.click && !this.isPersonCardVisible) {
this.showPersonCard();
} else {
this._hidePersonCard();
this.hidePersonCard();
}
}

private _handleMouseEnter(e: MouseEvent) {
private handleMouseEnter(e: MouseEvent) {
clearTimeout(this._mouseEnterTimeout);
clearTimeout(this._mouseLeaveTimeout);
if (this.personCardInteraction !== PersonCardInteraction.hover) {
return;
}
this._mouseEnterTimeout = setTimeout(this._showPersonCard.bind(this), 500);
this._mouseEnterTimeout = setTimeout(this.showPersonCard.bind(this), 500);
}

private _handleMouseLeave(e: MouseEvent) {
private handleMouseLeave(e: MouseEvent) {
clearTimeout(this._mouseEnterTimeout);
clearTimeout(this._mouseLeaveTimeout);
this._mouseLeaveTimeout = setTimeout(this._hidePersonCard.bind(this), 500);
this._mouseLeaveTimeout = setTimeout(this.hidePersonCard.bind(this), 500);
}

private _showPersonCard() {
if (!this._personCardShouldRender) {
this._personCardShouldRender = true;
private showPersonCard() {
if (!this.personCardShouldRender) {
this.personCardShouldRender = true;
}

this._isPersonCardVisible = true;
this.isPersonCardVisible = true;
}

private _hidePersonCard() {
this._isPersonCardVisible = false;
const personCard = this.querySelector('mgt-person-card') as MgtPersonCard;
private hidePersonCard() {
this.isPersonCardVisible = false;
const personCard = (this.querySelector('mgt-person-card') ||
this.renderRoot.querySelector('mgt-person-card')) as MgtPersonCard;
if (personCard) {
personCard.isExpanded = false;
}
Expand All @@ -332,46 +335,28 @@ export class MgtPerson extends MgtTemplatedComponent {
return null;
}

private renderPersonCard() {
// ensure person card is only rendered when needed
if (this.personCardInteraction === PersonCardInteraction.none || !this._personCardShouldRender) {
return;
}
// logic for rendering left if there is no space
const personRect = this.renderRoot.querySelector('.root').getBoundingClientRect();
const leftEdge = personRect.left;
const rightEdge = (window.innerWidth || document.documentElement.clientWidth) - personRect.right;
this._openLeft = rightEdge < leftEdge;

// logic for rendering up
const bottomEdge = (window.innerHeight || document.documentElement.clientHeight) - personRect.bottom;
this._openUp = bottomEdge < 175;

// find position to renderup to
let customStyle = null;
if (this._openUp) {
const personSize = this.getBoundingClientRect().bottom - this.getBoundingClientRect().top;
customStyle = `bottom: ${personSize / 2 + 8}px`;
private renderFlyout(anchor: TemplateResult) {
if (this.personCardInteraction === PersonCardInteraction.none) {
return anchor;
}

const flyoutClasses = {
flyout: true,
openLeft: this._openLeft,
openUp: this._openUp,
visible: this._isPersonCardVisible
};
if (this._isPersonCardVisible) {
const image = this.getImage();
const image = this.getImage();
const flyout = this.personCardShouldRender
? html`
<div slot="flyout" class="flyout">
${this.renderTemplate('person-card', { person: this.personDetails, personImage: image }) ||
html`
<mgt-person-card .personDetails=${this.personDetails} .personImage=${image}> </mgt-person-card>
`}
</div>
`
: null;

return html`
<div style="${customStyle}" class=${classMap(flyoutClasses)}>
${this.renderTemplate('person-card', { person: this.personDetails, personImage: image }) ||
html`
<mgt-person-card .personDetails=${this.personDetails} .personImage=${image}> </mgt-person-card>
`}
</div>
`;
}
return html`
<mgt-flyout .isOpen=${this.isPersonCardVisible}>
${anchor} ${flyout}
</mgt-flyout>
`;
}

private renderDetails() {
Expand Down
9 changes: 2 additions & 7 deletions packages/mgt/src/components/mgt-tasks/mgt-tasks.scss
Original file line number Diff line number Diff line change
Expand Up @@ -198,21 +198,16 @@ mgt-tasks,
}
.Picker {
background-color: white;
display: block;
position: absolute;
box-shadow: 0 3px 7px rgba(0, 0, 0, 0.3);
-webkit-background-clip: padding-box;
-moz-background-clip: padding-box;
background-clip: padding-box;
width: 450px;
width: 350px;
color: var(--task-detail-color, black);
z-index: 1;
margin: 8px;
mgt-people-picker {
--separator-margin: 0px 10px 0px 10px;
}
&.Hidden {
display: none;
}
}

input,
Expand Down
Loading

0 comments on commit 89afe03

Please sign in to comment.