MOBILE-2353 rte: Improve editor with resizing
This commit is contained in:
parent
ea6bc89cfd
commit
c492921df1
@ -19,6 +19,5 @@
|
|||||||
|
|
||||||
<!-- Edit -->
|
<!-- Edit -->
|
||||||
<ion-item text-wrap *ngIf="edit && loaded">
|
<ion-item text-wrap *ngIf="edit && loaded">
|
||||||
<!-- @todo: [component]="component" [componentId]="assign.cmid" -->
|
<core-rich-text-editor item-content [control]="control" [placeholder]="plugin.name" name="assignfeedbackcomments_editor" [component]="component" [componentId]="assign.cmid"></core-rich-text-editor>
|
||||||
<core-rich-text-editor item-content [control]="control" [placeholder]="plugin.name" name="assignfeedbackcomments_editor"></core-rich-text-editor>
|
|
||||||
</ion-item>
|
</ion-item>
|
||||||
|
@ -15,7 +15,6 @@
|
|||||||
<p>{{ 'core.numwords' | translate: {'$a': words + ' / ' + configs.wordlimit} }}</p>
|
<p>{{ 'core.numwords' | translate: {'$a': words + ' / ' + configs.wordlimit} }}</p>
|
||||||
</ion-item>
|
</ion-item>
|
||||||
<ion-item text-wrap>
|
<ion-item text-wrap>
|
||||||
<!-- @todo: [component]="component" [componentId]="assign.cmid" -->
|
<core-rich-text-editor item-content [control]="control" [placeholder]="plugin.name" name="onlinetext_editor_text" (contentChanged)="onChange($event)" [component]="component" [componentId]="assign.cmid"></core-rich-text-editor>
|
||||||
<core-rich-text-editor item-content [control]="control" [placeholder]="plugin.name" name="onlinetext_editor_text" (contentChanged)="onChange($event)"></core-rich-text-editor>
|
|
||||||
</ion-item>
|
</ion-item>
|
||||||
</div>
|
</div>
|
||||||
|
@ -38,9 +38,7 @@
|
|||||||
</ion-item>
|
</ion-item>
|
||||||
<ion-item>
|
<ion-item>
|
||||||
<ion-label stacked>{{ 'addon.mod_forum.message' | translate }}</ion-label>
|
<ion-label stacked>{{ 'addon.mod_forum.message' | translate }}</ion-label>
|
||||||
<core-rich-text-editor item-content [control]="messageControl" (contentChanged)="onMessageChange($event)" [placeholder]="'addon.mod_forum.message' | translate" [name]="'mod_forum_reply_' + post.id"></core-rich-text-editor>
|
<core-rich-text-editor item-content [control]="messageControl" (contentChanged)="onMessageChange($event)" [placeholder]="'addon.mod_forum.message' | translate" [name]="'mod_forum_reply_' + post.id" [component]="component" [componentId]="componentId"></core-rich-text-editor>
|
||||||
<!-- @todo: Attributes that were passed to RTE in Ionic 1 but now they aren't supported yet:
|
|
||||||
[component]="component" [componentId]="componentId" -->
|
|
||||||
</ion-item>
|
</ion-item>
|
||||||
<core-attachments *ngIf="forum.id && forum.maxattachments > 0" [files]="replyData.files" [maxSize]="forum.maxbytes" [maxSubmissions]="forum.maxattachments" [component]="component" [componentId]="forum.cmid" [allowOffline]="true"></core-attachments>
|
<core-attachments *ngIf="forum.id && forum.maxattachments > 0" [files]="replyData.files" [maxSize]="forum.maxbytes" [maxSubmissions]="forum.maxattachments" [component]="component" [componentId]="forum.cmid" [allowOffline]="true"></core-attachments>
|
||||||
<ion-grid>
|
<ion-grid>
|
||||||
|
@ -19,9 +19,7 @@
|
|||||||
</ion-item>
|
</ion-item>
|
||||||
<ion-item>
|
<ion-item>
|
||||||
<ion-label stacked>{{ 'addon.mod_forum.message' | translate }}</ion-label>
|
<ion-label stacked>{{ 'addon.mod_forum.message' | translate }}</ion-label>
|
||||||
<core-rich-text-editor item-content [control]="messageControl" (contentChanged)="onMessageChange($event)" [placeholder]="'addon.mod_forum.message' | translate" name="addon_mod_forum_new_discussion"></core-rich-text-editor>
|
<core-rich-text-editor item-content [control]="messageControl" (contentChanged)="onMessageChange($event)" [placeholder]="'addon.mod_forum.message' | translate" name="addon_mod_forum_new_discussion" [component]="component" [componentId]="forum.cmid"></core-rich-text-editor>
|
||||||
<!-- @todo: Attributes that were passed to RTE in Ionic 1 but now they aren't supported yet:
|
|
||||||
[component]="component" [componentId]="forum.cmid" -->
|
|
||||||
</ion-item>
|
</ion-item>
|
||||||
<ion-item *ngIf="showGroups">
|
<ion-item *ngIf="showGroups">
|
||||||
<ion-label id="addon-mod-forum-groupslabel">{{ 'addon.mod_forum.group' | translate }}</ion-label>
|
<ion-label id="addon-mod-forum-groupslabel">{{ 'addon.mod_forum.group' | translate }}</ion-label>
|
||||||
|
@ -5,6 +5,13 @@ $addon-mod-wiki-toc-border-color: $gray-dark !default;
|
|||||||
$addon-mod-wiki-toc-background-color: $gray-light !default;
|
$addon-mod-wiki-toc-background-color: $gray-light !default;
|
||||||
|
|
||||||
addon-mod-wiki-index {
|
addon-mod-wiki-index {
|
||||||
|
background-color: $white;
|
||||||
|
|
||||||
|
.core-tabs-content-container,
|
||||||
|
.addon-mod_wiki-page-content {
|
||||||
|
background-color: $white;
|
||||||
|
}
|
||||||
|
|
||||||
.wiki-toc {
|
.wiki-toc {
|
||||||
border: 1px solid $addon-mod-wiki-toc-border-color;
|
border: 1px solid $addon-mod-wiki-toc-border-color;
|
||||||
background: $addon-mod-wiki-toc-background-color;
|
background: $addon-mod-wiki-toc-background-color;
|
||||||
|
@ -17,8 +17,7 @@
|
|||||||
</ion-item>
|
</ion-item>
|
||||||
|
|
||||||
<ion-item>
|
<ion-item>
|
||||||
<!-- @todo: [component]="component" [componentId]="componentId" -->
|
<core-rich-text-editor item-content [control]="contentControl" [placeholder]="'core.content' | translate" name="wiki_page_content" [component]="component" [componentId]="componentId"></core-rich-text-editor>
|
||||||
<core-rich-text-editor item-content [control]="contentControl" [placeholder]="'core.content' | translate" name="wiki_page_content"></core-rich-text-editor>
|
|
||||||
</ion-item>
|
</ion-item>
|
||||||
|
|
||||||
<ion-badge color="danger" *ngIf="wrongVersionLock" item-end>{{ 'addon.mod_wiki.wrongversionlock' | translate }}</ion-badge> <!-- @todo: Check this. -->
|
<ion-badge color="danger" *ngIf="wrongVersionLock" item-end>{{ 'addon.mod_wiki.wrongversionlock' | translate }}</ion-badge> <!-- @todo: Check this. -->
|
||||||
|
@ -11,9 +11,7 @@
|
|||||||
<!-- Plain text textarea. -->
|
<!-- Plain text textarea. -->
|
||||||
<ion-textarea *ngIf="question.isPlainText" class="core-question-textarea" [ngClass]='{"core-monospaced": question.isMonospaced}' placeholder="{{ 'core.question.answer' | translate }}" [attr.name]="question.textarea.name" aria-multiline="true" [ngModel]="question.textarea.text"></ion-textarea>
|
<ion-textarea *ngIf="question.isPlainText" class="core-question-textarea" [ngClass]='{"core-monospaced": question.isMonospaced}' placeholder="{{ 'core.question.answer' | translate }}" [attr.name]="question.textarea.name" aria-multiline="true" [ngModel]="question.textarea.text"></ion-textarea>
|
||||||
<!-- Rich text editor. -->
|
<!-- Rich text editor. -->
|
||||||
<core-rich-text-editor item-content *ngIf="!question.isPlainText" placeholder="{{ 'core.question.answer' | translate }}" [control]="formControl" [name]="question.textarea.name"></core-rich-text-editor>
|
<core-rich-text-editor item-content *ngIf="!question.isPlainText" placeholder="{{ 'core.question.answer' | translate }}" [control]="formControl" [name]="question.textarea.name" [component]="component" [componentId]="componentId"></core-rich-text-editor>
|
||||||
<!-- @todo: Attributes that were passed to RTE in Ionic 1 but now they aren't supported yet:
|
|
||||||
[component]="component" [componentId]="componentId" -->
|
|
||||||
</ion-item>
|
</ion-item>
|
||||||
|
|
||||||
<!-- Draft files not supported. -->
|
<!-- Draft files not supported. -->
|
||||||
|
@ -32,7 +32,7 @@
|
|||||||
.img-responsive {
|
.img-responsive {
|
||||||
display: block;
|
display: block;
|
||||||
max-width: 100%;
|
max-width: 100%;
|
||||||
/* height: auto; */
|
height: auto;
|
||||||
}
|
}
|
||||||
|
|
||||||
.opacity-hide { opacity: 0; }
|
.opacity-hide { opacity: 0; }
|
||||||
|
@ -3,7 +3,8 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- https://developer.mozilla.org/en-US/docs/Web/API/Document/execCommand -->
|
<!-- https://developer.mozilla.org/en-US/docs/Web/API/Document/execCommand -->
|
||||||
<div #decorate class="formatOptions">
|
<div #decorate class="core-rte-toolbar">
|
||||||
|
<div class="core-rte-buttons">
|
||||||
<button data-command="bold"><strong>B</strong></button>
|
<button data-command="bold"><strong>B</strong></button>
|
||||||
<button data-command="italic"><i>I</i></button>
|
<button data-command="italic"><i>I</i></button>
|
||||||
<button data-command="underline"><u>U</u></button>
|
<button data-command="underline"><u>U</u></button>
|
||||||
@ -11,18 +12,21 @@
|
|||||||
<button data-command="formatBlock|<h1>">H1</button>
|
<button data-command="formatBlock|<h1>">H1</button>
|
||||||
<button data-command="formatBlock|<h2>">H2</button>
|
<button data-command="formatBlock|<h2>">H2</button>
|
||||||
<button data-command="formatBlock|<h3>">H3</button>
|
<button data-command="formatBlock|<h3>">H3</button>
|
||||||
<button data-command="formatBlock|<pre>">Pre</button>
|
<button data-command="formatBlock|<pre>"><pre></button>
|
||||||
<button data-command="insertOrderedList">OL</button>
|
<button data-command="insertOrderedList"><ion-icon name="list" md="ios-list"></ion-icon></button>
|
||||||
<button data-command="insertUnorderedList">UL</button>
|
<button data-command="insertUnorderedList">1,2,3</button>
|
||||||
<button data-command="removeFormat">Tx</button>
|
<button data-command="removeFormat"><ion-icon name="brush"></ion-icon></button>
|
||||||
<button (click)="toggleEditor($event)">Toggle Editor</button>
|
<button (click)="toggleEditor($event)"><ion-icon name="eye-off"></ion-icon> {{ 'core.viewcode' | translate }}</button>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div [hidden]="rteEnabled">
|
<div [hidden]="rteEnabled">
|
||||||
<ion-textarea #textarea class="core-textarea" [placeholder]="placeholder" [attr.name]="name" ngControl="control" (ionChange)="onChange($event)"></ion-textarea>
|
<ion-textarea #textarea class="core-textarea" [placeholder]="placeholder" [attr.name]="name" ngControl="control" (ionChange)="onChange($event)"></ion-textarea>
|
||||||
<div class="formatOptions">
|
<div class="core-rte-toolbar">
|
||||||
<button tappable (click)="toggleEditor($event)">Toggle Editor</button>
|
<div #decorate class="core-rte-buttons">
|
||||||
|
<button tappable (click)="toggleEditor($event)"><ion-icon name="eye"></ion-icon> {{ 'core.vieweditor' | translate }}</button>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
@ -10,7 +10,6 @@ core-rich-text-editor {
|
|||||||
display: flex;
|
display: flex;
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
}
|
}
|
||||||
|
|
||||||
.core-rte-editor, .core-textarea {
|
.core-rte-editor, .core-textarea {
|
||||||
padding: 2px;
|
padding: 2px;
|
||||||
margin: 2px;
|
margin: 2px;
|
||||||
@ -51,21 +50,33 @@ core-rich-text-editor {
|
|||||||
overflow-y: auto;
|
overflow-y: auto;
|
||||||
}
|
}
|
||||||
|
|
||||||
div.formatOptions {
|
div.core-rte-toolbar {
|
||||||
background: $gray-dark;
|
background: $gray-darker;
|
||||||
margin: 5px 1px 15px 1px;
|
margin: 0px 1px 15px 1px;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
flex-grow: 0;
|
flex-grow: 0;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
z-index: 1;
|
z-index: 1;
|
||||||
|
|
||||||
|
.core-rte-buttons {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
flex-direction: row;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
justify-content: space-evenly;
|
||||||
|
|
||||||
button {
|
button {
|
||||||
background: $gray-dark;
|
background: $gray-darker;
|
||||||
color: $white;
|
color: $white;
|
||||||
font-size: 1.1em;
|
font-size: 1.1em;
|
||||||
height: 35px;
|
height: 35px;
|
||||||
min-width: 30px;
|
min-width: 30px;
|
||||||
padding-left: 1px;
|
padding-left: 3px;
|
||||||
padding-right: 1px;
|
padding-right: 3px;
|
||||||
|
border-right: 1px solid $gray-dark;
|
||||||
|
border-bottom: 1px solid $gray-dark;
|
||||||
|
flex-grow: 1;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -12,9 +12,13 @@
|
|||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
import { Component, Input, Output, EventEmitter, ViewChild, ElementRef, AfterContentInit, OnDestroy } from '@angular/core';
|
import { Component, Input, Output, EventEmitter, ViewChild, ElementRef, AfterContentInit, OnDestroy, Optional }
|
||||||
import { TextInput } from 'ionic-angular';
|
from '@angular/core';
|
||||||
|
import { TextInput, Content } from 'ionic-angular';
|
||||||
|
import { CoreSitesProvider } from '@providers/sites';
|
||||||
|
import { CoreFilepoolProvider } from '@providers/filepool';
|
||||||
import { CoreDomUtilsProvider } from '@providers/utils/dom';
|
import { CoreDomUtilsProvider } from '@providers/utils/dom';
|
||||||
|
import { CoreUrlUtilsProvider } from '@providers/utils/url';
|
||||||
import { FormControl } from '@angular/forms';
|
import { FormControl } from '@angular/forms';
|
||||||
import { Keyboard } from '@ionic-native/keyboard';
|
import { Keyboard } from '@ionic-native/keyboard';
|
||||||
import { Subscription } from 'rxjs';
|
import { Subscription } from 'rxjs';
|
||||||
@ -39,25 +43,32 @@ import { Subscription } from 'rxjs';
|
|||||||
})
|
})
|
||||||
export class CoreRichTextEditorComponent implements AfterContentInit, OnDestroy {
|
export class CoreRichTextEditorComponent implements AfterContentInit, OnDestroy {
|
||||||
// Based on: https://github.com/judgewest2000/Ionic3RichText/
|
// Based on: https://github.com/judgewest2000/Ionic3RichText/
|
||||||
// @todo: Resize, images, anchor button, fullscreen...
|
// @todo: Anchor button, fullscreen...
|
||||||
|
|
||||||
@Input() placeholder = ''; // Placeholder to set in textarea.
|
@Input() placeholder = ''; // Placeholder to set in textarea.
|
||||||
@Input() control: FormControl; // Form control.
|
@Input() control: FormControl; // Form control.
|
||||||
@Input() name = 'core-rich-text-editor'; // Name to set to the textarea.
|
@Input() name = 'core-rich-text-editor'; // Name to set to the textarea.
|
||||||
|
@Input() component?: string; // The component to link the files to.
|
||||||
|
@Input() componentId?: number; // An ID to use in conjunction with the component.
|
||||||
@Output() contentChanged: EventEmitter<string>;
|
@Output() contentChanged: EventEmitter<string>;
|
||||||
|
|
||||||
@ViewChild('editor') editor: ElementRef; // WYSIWYG editor.
|
@ViewChild('editor') editor: ElementRef; // WYSIWYG editor.
|
||||||
@ViewChild('textarea') textarea: TextInput; // Textarea editor.
|
@ViewChild('textarea') textarea: TextInput; // Textarea editor.
|
||||||
@ViewChild('decorate') decorate: ElementRef; // Buttons.
|
@ViewChild('decorate') decorate: ElementRef; // Buttons.
|
||||||
|
|
||||||
rteEnabled = false;
|
protected element: HTMLDivElement;
|
||||||
uniqueId = `rte{Math.floor(Math.random() * 1000000)}`;
|
protected editorElement: HTMLDivElement;
|
||||||
editorElement: HTMLDivElement;
|
protected resizeFunction;
|
||||||
|
|
||||||
protected valueChangeSubscription: Subscription;
|
protected valueChangeSubscription: Subscription;
|
||||||
|
|
||||||
constructor(private domUtils: CoreDomUtilsProvider, private keyboard: Keyboard) {
|
rteEnabled = false;
|
||||||
|
|
||||||
|
constructor(private domUtils: CoreDomUtilsProvider, private keyboard: Keyboard, private urlUtils: CoreUrlUtilsProvider,
|
||||||
|
private sitesProvider: CoreSitesProvider, private filepoolProvider: CoreFilepoolProvider,
|
||||||
|
@Optional() private content: Content, elementRef: ElementRef) {
|
||||||
this.contentChanged = new EventEmitter<string>();
|
this.contentChanged = new EventEmitter<string>();
|
||||||
|
this.element = elementRef.nativeElement as HTMLDivElement;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -104,6 +115,58 @@ export class CoreRichTextEditorComponent implements AfterContentInit, OnDestroy
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
this.treatExternalContent();
|
||||||
|
|
||||||
|
this.resizeFunction = this.maximizeEditorSize.bind(this);
|
||||||
|
window.addEventListener('resize', this.resizeFunction);
|
||||||
|
setTimeout(this.resizeFunction, 1000);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Resize editor to maximize the space occupied.
|
||||||
|
*/
|
||||||
|
protected maximizeEditorSize(): void {
|
||||||
|
this.content.resize();
|
||||||
|
const contentVisibleHeight = this.content.contentHeight;
|
||||||
|
|
||||||
|
// Editor is ready, adjust Height if needed.
|
||||||
|
if (contentVisibleHeight > 0) {
|
||||||
|
const height = this.getSurroundingHeight(this.element);
|
||||||
|
if (contentVisibleHeight > height) {
|
||||||
|
this.element.style.height = this.domUtils.formatPixelsSize(contentVisibleHeight - height);
|
||||||
|
} else {
|
||||||
|
this.element.style.height = '';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the height of the surrounding elements from the current to the top element.
|
||||||
|
*
|
||||||
|
* @param {any} element Directive DOM element to get surroundings elements from.
|
||||||
|
* @return {number} Surrounding height in px.
|
||||||
|
*/
|
||||||
|
protected getSurroundingHeight(element: any): number {
|
||||||
|
let height = 0;
|
||||||
|
|
||||||
|
while (element.parentNode && element.parentNode.tagName != 'ION-CONTENT') {
|
||||||
|
const parent = element.parentNode;
|
||||||
|
if (element.tagName && element.tagName != 'CORE-LOADING') {
|
||||||
|
parent.childNodes.forEach((child) => {
|
||||||
|
if (child.tagName && child != element) {
|
||||||
|
height += this.domUtils.getElementHeight(child, false, true, true);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
element = parent;
|
||||||
|
}
|
||||||
|
|
||||||
|
const cs = getComputedStyle(element);
|
||||||
|
height += this.domUtils.getComputedStyleMeasure(cs, 'paddingTop') +
|
||||||
|
this.domUtils.getComputedStyleMeasure(cs, 'paddingBottom');
|
||||||
|
|
||||||
|
return height;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -171,6 +234,30 @@ export class CoreRichTextEditorComponent implements AfterContentInit, OnDestroy
|
|||||||
}, 1);
|
}, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Treat elements that can contain external content.
|
||||||
|
* We only search for images because the editor should receive unfiltered text, so the multimedia filter won't be applied.
|
||||||
|
* Treating videos and audios in here is complex, so if a user manually adds one he won't be able to play it in the editor.
|
||||||
|
*/
|
||||||
|
protected treatExternalContent(): void {
|
||||||
|
const elements = Array.from(this.editorElement.querySelectorAll('img')),
|
||||||
|
siteId = this.sitesProvider.getCurrentSiteId(),
|
||||||
|
canDownloadFiles = this.sitesProvider.getCurrentSite().canDownloadFiles();
|
||||||
|
elements.forEach((el) => {
|
||||||
|
const url = el.src;
|
||||||
|
|
||||||
|
if (!url || !this.urlUtils.isDownloadableUrl(url) || (!canDownloadFiles && this.urlUtils.isPluginFileUrl(url))) {
|
||||||
|
// Nothing to treat.
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check if it's downloaded.
|
||||||
|
return this.filepoolProvider.getSrcByUrl(siteId, url, this.component, this.componentId).then((finalUrl) => {
|
||||||
|
el.setAttribute('src', finalUrl);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Check if text is empty.
|
* Check if text is empty.
|
||||||
* @param {string} value text
|
* @param {string} value text
|
||||||
@ -215,5 +302,6 @@ export class CoreRichTextEditorComponent implements AfterContentInit, OnDestroy
|
|||||||
*/
|
*/
|
||||||
ngOnDestroy(): void {
|
ngOnDestroy(): void {
|
||||||
this.valueChangeSubscription && this.valueChangeSubscription.unsubscribe();
|
this.valueChangeSubscription && this.valueChangeSubscription.unsubscribe();
|
||||||
|
window.removeEventListener('resize', this.resizeFunction);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -227,6 +227,8 @@
|
|||||||
"usernotfullysetup": "User not fully set-up",
|
"usernotfullysetup": "User not fully set-up",
|
||||||
"users": "Users",
|
"users": "Users",
|
||||||
"view": "View",
|
"view": "View",
|
||||||
|
"viewcode": "View code",
|
||||||
|
"vieweditor": "View editor",
|
||||||
"viewprofile": "View profile",
|
"viewprofile": "View profile",
|
||||||
"warningofflinedatadeleted": "Offline data of {{component}} '{{name}}' has been deleted. {{error}}",
|
"warningofflinedatadeleted": "Offline data of {{component}} '{{name}}' has been deleted. {{error}}",
|
||||||
"whatisyourage": "What is your age?",
|
"whatisyourage": "What is your age?",
|
||||||
|
@ -365,13 +365,16 @@ export class CoreDomUtilsProvider {
|
|||||||
let surround = 0;
|
let surround = 0;
|
||||||
|
|
||||||
if (usePadding) {
|
if (usePadding) {
|
||||||
surround += parseInt(computedStyle['padding' + priorSide], 10) + parseInt(computedStyle['padding' + afterSide], 10);
|
surround += this.getComputedStyleMeasure(computedStyle, 'padding' + priorSide) +
|
||||||
|
this.getComputedStyleMeasure(computedStyle, 'padding' + afterSide);
|
||||||
}
|
}
|
||||||
if (useMargin) {
|
if (useMargin) {
|
||||||
surround += parseInt(computedStyle['margin' + priorSide], 10) + parseInt(computedStyle['margin' + afterSide], 10);
|
surround += this.getComputedStyleMeasure(computedStyle, 'margin' + priorSide) +
|
||||||
|
this.getComputedStyleMeasure(computedStyle, 'margin' + afterSide);
|
||||||
}
|
}
|
||||||
if (useBorder) {
|
if (useBorder) {
|
||||||
surround += parseInt(computedStyle['border' + priorSide], 10) + parseInt(computedStyle['border' + afterSide], 10);
|
surround += this.getComputedStyleMeasure(computedStyle, 'border' + priorSide + 'Width') +
|
||||||
|
this.getComputedStyleMeasure(computedStyle, 'border' + afterSide + 'Width');
|
||||||
}
|
}
|
||||||
if (innerMeasure) {
|
if (innerMeasure) {
|
||||||
measure = measure > surround ? measure - surround : 0;
|
measure = measure > surround ? measure - surround : 0;
|
||||||
@ -381,7 +384,17 @@ export class CoreDomUtilsProvider {
|
|||||||
}
|
}
|
||||||
|
|
||||||
return measure;
|
return measure;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the computed style measure or 0 if not found or NaN.
|
||||||
|
*
|
||||||
|
* @param {any} style Style from getComputedStyle.
|
||||||
|
* @param {string} measure Measure to get.
|
||||||
|
* @return {number} Result of the measure.
|
||||||
|
*/
|
||||||
|
getComputedStyleMeasure(style: any, measure: string): number {
|
||||||
|
return parseInt(style[measure], 10) || 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
Loading…
x
Reference in New Issue
Block a user