UNPKG

@knotes/nativescript-keyboard-toolbar

Version:

NativeScript Keyboard Toolbar plugin

132 lines (131 loc) 6.43 kB
import { Application as application, Screen as screen, } from '@nativescript/core'; import { EditableTextBase } from "@nativescript/core/ui/editable-text-base"; import { AnimationCurve } from "@nativescript/core/ui/enums"; import { Page } from "@nativescript/core/ui/page"; import { Frame } from "@nativescript/core/ui/frame"; import { ToolbarBase } from "./keyboard-toolbar.common"; export class Toolbar extends ToolbarBase { _loaded() { this.keyboardNotificationObserver = application.ios.addNotificationObserver(UIKeyboardWillChangeFrameNotification, notification => { const newKeyboardHeight = notification.userInfo.valueForKey(UIKeyboardFrameEndUserInfoKey).CGRectValue.size.height; if (newKeyboardHeight === this.lastKeyboardHeight) { return; } const isFirstAnimation = this.lastKeyboardHeight === undefined; this.lastKeyboardHeight = newKeyboardHeight; if (!isFirstAnimation && this.hasFocus) { const parent = this.content.parent; parent.translateY = this.startPositionY - newKeyboardHeight - (this.lastHeight / screen.mainScreen.scale); } }); const onViewForIdFound = forView => { const parent = this.content.parent; const isText = forView instanceof EditableTextBase; const hasIQKeyboardManagerInstalled = typeof (IQKeyboardManager) !== "undefined"; const iqKeyboardManagerOriginalDistance = hasIQKeyboardManagerInstalled ? IQKeyboardManager.sharedManager().keyboardDistanceFromTextField : 0; if (isText) { forView.on("focus", () => { if (hasIQKeyboardManagerInstalled) { IQKeyboardManager.sharedManager().keyboardDistanceFromTextField = iqKeyboardManagerOriginalDistance + parent.height; } this.hasFocus = true; setTimeout(() => { const animateToY = this.startPositionY - this.lastKeyboardHeight - (this.showWhenKeyboardHidden === true ? 0 : (this.lastHeight / screen.mainScreen.scale)); this.log("focus, animateToY: " + animateToY); parent.animate({ translate: { x: 0, y: animateToY }, curve: AnimationCurve.cubicBezier(.32, .49, .56, 1), duration: 370 }).then(() => { }); }); }); forView.on("blur", () => { if (hasIQKeyboardManagerInstalled) { IQKeyboardManager.sharedManager().keyboardDistanceFromTextField = iqKeyboardManagerOriginalDistance; } this.hasFocus = false; const animateToY = this.showWhenKeyboardHidden === true && this.showAtBottomWhenKeyboardHidden !== true ? 0 : this.startPositionY; this.log("blur, animateToY: " + animateToY); parent.animate({ translate: { x: 0, y: animateToY }, curve: AnimationCurve.cubicBezier(.32, .49, .56, 1), duration: 370 }).then(() => { }); }); } else { forView.on("tap", () => { const animateToY = this.startPositionY - (this.lastHeight / screen.mainScreen.scale); this.log("tap, animateToY: " + animateToY); parent.animate({ translate: { x: 0, y: animateToY }, curve: AnimationCurve.cubicBezier(.32, .49, .56, 1), duration: 370 }).then(() => { }); }); } }; this.getViewForId(10) .then(view => onViewForIdFound(view)) .catch(() => console.log(`\n⌨ ⌨ ⌨ Please make sure forId="<view id>" resolves to a visible view, or the toolbar won't render correctly! Example: <Toolbar forId="myId" height="44">\n\n`)); } getViewForId(attemptsLeft) { return new Promise((resolve, reject) => { if (attemptsLeft-- > 0) { setTimeout(() => { let pg; if (Frame.topmost()) { pg = Frame.topmost().currentPage; } else { pg = this.content.parent; while (pg && !(pg instanceof Page)) { pg = pg.parent; } } const page = pg; const found = page && page.modal ? page.modal.getViewById(this.forId) : page && page.getViewById(this.forId); if (found) { resolve(found); } else { this.getViewForId(attemptsLeft).then(resolve).catch(reject); } }, 200); } else { reject(); } }); } _unloaded() { application.ios.removeNotificationObserver(this.keyboardNotificationObserver, UIKeyboardWillChangeFrameNotification); } _layout(left, top, right, bottom) { const parent = this.content.parent; const newHeight = parent.getMeasuredHeight(); if (newHeight === this.lastHeight) { return; } const { y } = parent.getLocationOnScreen(); this.startPositionY = screen.mainScreen.heightDIPs - y - ((this.showWhenKeyboardHidden === true ? newHeight : 0) / screen.mainScreen.scale); this.log("_layout, startPositionY: " + this.startPositionY); if (this.lastHeight === undefined) { if (this.showWhenKeyboardHidden === true) { if (this.showAtBottomWhenKeyboardHidden === true) { parent.translateY = this.startPositionY; } } else { parent.translateY = this.startPositionY; } } else if (this.lastHeight !== newHeight) { parent.translateY = this.startPositionY; } this.lastHeight = newHeight; } }