mirror of
https://github.com/NativeScript/NativeScript.git
synced 2025-08-18 13:51:27 +08:00
fix(button): ios let the gesture observer handles tap events
in some weird cases like i some UICollectionView layouts the UIControlEvents.TouchUpInside is failing
This commit is contained in:
@ -51,7 +51,7 @@ export function createPage() {
|
|||||||
//page.content = GridLayout;
|
//page.content = GridLayout;
|
||||||
page.content = StackLayout;
|
page.content = StackLayout;
|
||||||
var x = 1;
|
var x = 1;
|
||||||
btn1.on(button.Button.tapEvent, function () {
|
btn1.on(button.tapEvent, function () {
|
||||||
x++;
|
x++;
|
||||||
var gravity;
|
var gravity;
|
||||||
//btn1.android.setLayoutParams(new android.view.ViewGroup.LayoutParams(android.view.ViewGroup.LayoutParams.FILL_PARENT, android.view.ViewGroup.LayoutParams.FILL_PARENT));
|
//btn1.android.setLayoutParams(new android.view.ViewGroup.LayoutParams(android.view.ViewGroup.LayoutParams.FILL_PARENT, android.view.ViewGroup.LayoutParams.FILL_PARENT));
|
||||||
|
@ -13,7 +13,7 @@ export function createPage() {
|
|||||||
var vAligns: VerticalAlignment[] = ['stretch', 'top', 'middle', 'bottom'];
|
var vAligns: VerticalAlignment[] = ['stretch', 'top', 'middle', 'bottom'];
|
||||||
//var hAligns = ["stretch", "left", "center", "right"];
|
//var hAligns = ["stretch", "left", "center", "right"];
|
||||||
var count = 0;
|
var count = 0;
|
||||||
btn.on(buttons.Button.tapEvent, function () {
|
btn.on(buttons.tapEvent, function () {
|
||||||
//page.css = "button { vertical-align:" + vAligns[(count++) % 4] + " }";
|
//page.css = "button { vertical-align:" + vAligns[(count++) % 4] + " }";
|
||||||
btn.verticalAlignment = vAligns[count++ % 4];
|
btn.verticalAlignment = vAligns[count++ % 4];
|
||||||
});
|
});
|
||||||
|
@ -41,7 +41,7 @@ export function createPage() {
|
|||||||
var counter = 0;
|
var counter = 0;
|
||||||
var btn = new btns.Button();
|
var btn = new btns.Button();
|
||||||
btn.text = 'tap';
|
btn.text = 'tap';
|
||||||
btn.on(btns.Button.tapEvent, function () {
|
btn.on(btns.tapEvent, function () {
|
||||||
btn.text = 'hi: ' + counter++;
|
btn.text = 'hi: ' + counter++;
|
||||||
});
|
});
|
||||||
btn.isEnabled = false;
|
btn.isEnabled = false;
|
||||||
@ -52,7 +52,7 @@ export function createPage() {
|
|||||||
var info = new btns.Button();
|
var info = new btns.Button();
|
||||||
info.text = 'info';
|
info.text = 'info';
|
||||||
info.className = 'info';
|
info.className = 'info';
|
||||||
info.on(btns.Button.tapEvent, function () {
|
info.on(btns.tapEvent, function () {
|
||||||
info.text = 'hi: ' + counter++;
|
info.text = 'hi: ' + counter++;
|
||||||
btn.isEnabled = true;
|
btn.isEnabled = true;
|
||||||
});
|
});
|
||||||
|
@ -41,7 +41,7 @@ export function createPage() {
|
|||||||
var count = 0;
|
var count = 0;
|
||||||
var control = new btns.Button();
|
var control = new btns.Button();
|
||||||
control.text = 'test control';
|
control.text = 'test control';
|
||||||
control.on(btns.Button.tapEvent, (data) => {
|
control.on(btns.tapEvent, (data) => {
|
||||||
control.text = 'count: ' + count++;
|
control.text = 'count: ' + count++;
|
||||||
});
|
});
|
||||||
grid.addChild(control);
|
grid.addChild(control);
|
||||||
|
@ -6,7 +6,7 @@ import { Frame } from '@nativescript/core/ui/frame';
|
|||||||
import { Page } from '@nativescript/core/ui/page';
|
import { Page } from '@nativescript/core/ui/page';
|
||||||
import { ListView, ItemEventData } from '@nativescript/core/ui/list-view';
|
import { ListView, ItemEventData } from '@nativescript/core/ui/list-view';
|
||||||
import { BottomNavigation, TabContentItem, TabStrip, TabStripItem } from '@nativescript/core';
|
import { BottomNavigation, TabContentItem, TabStrip, TabStripItem } from '@nativescript/core';
|
||||||
import { Button } from '@nativescript/core/ui/button';
|
import { Button , tapEvent} from '@nativescript/core/ui/button';
|
||||||
|
|
||||||
var ASYNC = 2;
|
var ASYNC = 2;
|
||||||
|
|
||||||
@ -55,7 +55,7 @@ function _createListView(): ListView {
|
|||||||
var button = <Button>args.view;
|
var button = <Button>args.view;
|
||||||
if (!button) {
|
if (!button) {
|
||||||
button = new Button();
|
button = new Button();
|
||||||
button.on(Button.tapEvent, _clickHandlerFactory(args.index));
|
button.on(tapEvent, _clickHandlerFactory(args.index));
|
||||||
args.view = button;
|
args.view = button;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -3,6 +3,7 @@ import * as helper from '../../ui-helper';
|
|||||||
import { View, EventData, Button, Observable, Color, Page, FormattedString } from '@nativescript/core';
|
import { View, EventData, Button, Observable, Color, Page, FormattedString } from '@nativescript/core';
|
||||||
import * as buttonTestsNative from './button-tests-native';
|
import * as buttonTestsNative from './button-tests-native';
|
||||||
import * as spanModule from '@nativescript/core/text/span';
|
import * as spanModule from '@nativescript/core/text/span';
|
||||||
|
import { tapEvent} from '@nativescript/core/ui/button';
|
||||||
|
|
||||||
// >> button-require-others
|
// >> button-require-others
|
||||||
import { BindingOptions } from '@nativescript/core/ui/core/bindable';
|
import { BindingOptions } from '@nativescript/core/ui/core/bindable';
|
||||||
@ -100,7 +101,7 @@ var _testOnClick = function (views: Array<View>) {
|
|||||||
|
|
||||||
var actualValue = false;
|
var actualValue = false;
|
||||||
// >> button-tap
|
// >> button-tap
|
||||||
button.on(Button.tapEvent, function (args: EventData) {
|
button.on(tapEvent, function (args: EventData) {
|
||||||
// Do something
|
// Do something
|
||||||
// >> (hide)
|
// >> (hide)
|
||||||
actualValue = true;
|
actualValue = true;
|
||||||
|
@ -13,7 +13,7 @@ export class MyControl extends stackLayoutModule.StackLayout {
|
|||||||
lbl.id = 'my-test-label';
|
lbl.id = 'my-test-label';
|
||||||
var btn = new button.Button();
|
var btn = new button.Button();
|
||||||
btn.text = 'Tap me!';
|
btn.text = 'Tap me!';
|
||||||
btn.on(button.Button.tapEvent, (args: EventData) => {
|
btn.on(button.tapEvent, (args: EventData) => {
|
||||||
lbl.text = 'Tap ' + counter++;
|
lbl.text = 'Tap ' + counter++;
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -7,7 +7,7 @@ import { Frame } from '@nativescript/core/ui/frame';
|
|||||||
import { Page } from '@nativescript/core/ui/page';
|
import { Page } from '@nativescript/core/ui/page';
|
||||||
import { ListView, ItemEventData } from '@nativescript/core/ui/list-view';
|
import { ListView, ItemEventData } from '@nativescript/core/ui/list-view';
|
||||||
import { TabView, TabViewItem } from '@nativescript/core/ui/tab-view';
|
import { TabView, TabViewItem } from '@nativescript/core/ui/tab-view';
|
||||||
import { Button } from '@nativescript/core/ui/button';
|
import { Button, tapEvent} from '@nativescript/core/ui/button';
|
||||||
|
|
||||||
var ASYNC = 2;
|
var ASYNC = 2;
|
||||||
|
|
||||||
@ -44,7 +44,7 @@ function _createListView(): ListView {
|
|||||||
var button = <Button>args.view;
|
var button = <Button>args.view;
|
||||||
if (!button) {
|
if (!button) {
|
||||||
button = new Button();
|
button = new Button();
|
||||||
button.on(Button.tapEvent, _clickHandlerFactory(args.index));
|
button.on(tapEvent, _clickHandlerFactory(args.index));
|
||||||
args.view = button;
|
args.view = button;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
import { StackLayout, Label, Button, EventData } from '@nativescript/core';
|
import { StackLayout, Label, Button, EventData } from '@nativescript/core';
|
||||||
|
import { tapEvent } from '@nativescript/core/ui/button';
|
||||||
|
|
||||||
export class MyControl extends StackLayout {
|
export class MyControl extends StackLayout {
|
||||||
constructor() {
|
constructor() {
|
||||||
@ -9,7 +10,7 @@ export class MyControl extends StackLayout {
|
|||||||
var lbl = new Label();
|
var lbl = new Label();
|
||||||
var btn = new Button();
|
var btn = new Button();
|
||||||
btn.text = 'Tap me!';
|
btn.text = 'Tap me!';
|
||||||
btn.on(Button.tapEvent, (args: EventData) => {
|
btn.on(tapEvent, (args: EventData) => {
|
||||||
lbl.text = 'Tap ' + counter++;
|
lbl.text = 'Tap ' + counter++;
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -28,7 +28,7 @@ export function createPage() {
|
|||||||
//buttonTwoWay.automationText = "buttonTwoWay";
|
//buttonTwoWay.automationText = "buttonTwoWay";
|
||||||
|
|
||||||
buttonSetText.text = 'SetText';
|
buttonSetText.text = 'SetText';
|
||||||
buttonSetText.on(buttonModule.Button.tapEvent, function () {
|
buttonSetText.on(buttonModule.tapEvent, function () {
|
||||||
targetOneWay.text = 'Test';
|
targetOneWay.text = 'Test';
|
||||||
targetTwoWay.text = 'Test';
|
targetTwoWay.text = 'Test';
|
||||||
});
|
});
|
||||||
@ -47,7 +47,7 @@ export function createPage() {
|
|||||||
buttonOneWay.on(buttonModule.Button.loadedEvent, function () {
|
buttonOneWay.on(buttonModule.Button.loadedEvent, function () {
|
||||||
buttonOneWay.text = sourceOneWay.get('textSource');
|
buttonOneWay.text = sourceOneWay.get('textSource');
|
||||||
});
|
});
|
||||||
buttonOneWay.on(buttonModule.Button.tapEvent, function () {
|
buttonOneWay.on(buttonModule.tapEvent, function () {
|
||||||
buttonOneWay.text = sourceOneWay.get('textSource');
|
buttonOneWay.text = sourceOneWay.get('textSource');
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -67,7 +67,7 @@ export function createPage() {
|
|||||||
buttonTwoWay.on(buttonModule.Button.loadedEvent, function () {
|
buttonTwoWay.on(buttonModule.Button.loadedEvent, function () {
|
||||||
buttonTwoWay.text = sourceTwoWay.get('textSource');
|
buttonTwoWay.text = sourceTwoWay.get('textSource');
|
||||||
});
|
});
|
||||||
buttonTwoWay.on(buttonModule.Button.tapEvent, function () {
|
buttonTwoWay.on(buttonModule.tapEvent, function () {
|
||||||
buttonTwoWay.text = sourceTwoWay.get('textSource');
|
buttonTwoWay.text = sourceTwoWay.get('textSource');
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -16,7 +16,7 @@ export function stack0Loaded(args: observable.EventData) {
|
|||||||
target.bind(bindingOptions, source);
|
target.bind(bindingOptions, source);
|
||||||
source.set('textSource', 'Text');
|
source.set('textSource', 'Text');
|
||||||
|
|
||||||
button.on(buttonModule.Button.tapEvent, function () {
|
button.on(buttonModule.tapEvent, function () {
|
||||||
button.text = source.get('textSource');
|
button.text = source.get('textSource');
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -7,7 +7,7 @@ export function createPage() {
|
|||||||
|
|
||||||
var btn = new button.Button();
|
var btn = new button.Button();
|
||||||
btn.text = 'Alert';
|
btn.text = 'Alert';
|
||||||
btn.on(button.Button.tapEvent, function () {
|
btn.on(button.tapEvent, function () {
|
||||||
alert('Alert is global');
|
alert('Alert is global');
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
import { Observable } from '@nativescript/core/data/observable';
|
import { Observable } from '@nativescript/core/data/observable';
|
||||||
import { Button } from '@nativescript/core/ui/button';
|
import { Button, tapEvent } from '@nativescript/core/ui/button';
|
||||||
import { Color } from '@nativescript/core/color';
|
import { Color } from '@nativescript/core/color';
|
||||||
import { WrapLayout } from '@nativescript/core/ui/layouts/wrap-layout';
|
import { WrapLayout } from '@nativescript/core/ui/layouts/wrap-layout';
|
||||||
import { alert } from '@nativescript/core/ui/dialogs';
|
import { alert } from '@nativescript/core/ui/dialogs';
|
||||||
@ -65,7 +65,7 @@ export class TestPageMainViewModel extends Observable {
|
|||||||
btn.style.backgroundColor = new Color(this._colors[count++ % 3]);
|
btn.style.backgroundColor = new Color(this._colors[count++ % 3]);
|
||||||
btn.style.borderRadius = 5;
|
btn.style.borderRadius = 5;
|
||||||
btn.on(
|
btn.on(
|
||||||
Button.tapEvent,
|
tapEvent,
|
||||||
function (eventData) {
|
function (eventData) {
|
||||||
let text = btn.text;
|
let text = btn.text;
|
||||||
this.loadExample(text);
|
this.loadExample(text);
|
||||||
|
@ -259,6 +259,8 @@ export class ActionItems implements ActionItemsDefinition {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export class ActionItemBase extends ViewBase implements ActionItemDefinition {
|
export class ActionItemBase extends ViewBase implements ActionItemDefinition {
|
||||||
|
// defining this here means tap event wont be handled
|
||||||
|
// by the gesture observers
|
||||||
public static tapEvent = 'tap';
|
public static tapEvent = 'tap';
|
||||||
|
|
||||||
private _actionBar: ActionBarDefinition;
|
private _actionBar: ActionBarDefinition;
|
||||||
|
@ -3,9 +3,11 @@ import { TextBase } from '../text-base';
|
|||||||
import { CSSType } from '../core/view';
|
import { CSSType } from '../core/view';
|
||||||
import { booleanConverter } from '../core/view-base';
|
import { booleanConverter } from '../core/view-base';
|
||||||
|
|
||||||
|
|
||||||
|
export const tapEvent = 'tap';
|
||||||
|
|
||||||
@CSSType('Button')
|
@CSSType('Button')
|
||||||
export abstract class ButtonBase extends TextBase implements ButtonDefinition {
|
export abstract class ButtonBase extends TextBase implements ButtonDefinition {
|
||||||
public static tapEvent = 'tap';
|
|
||||||
|
|
||||||
get textWrap(): boolean {
|
get textWrap(): boolean {
|
||||||
return this.style.whiteSpace === 'normal';
|
return this.style.whiteSpace === 'normal';
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
import { ButtonBase } from './button-common';
|
import { ButtonBase, tapEvent } from './button-common';
|
||||||
import { PseudoClassHandler } from '../core/view';
|
import { PseudoClassHandler } from '../core/view';
|
||||||
import { paddingLeftProperty, paddingTopProperty, paddingRightProperty, paddingBottomProperty, Length, zIndexProperty, minWidthProperty, minHeightProperty } from '../styling/style-properties';
|
import { paddingLeftProperty, paddingTopProperty, paddingRightProperty, paddingBottomProperty, Length, zIndexProperty, minWidthProperty, minHeightProperty } from '../styling/style-properties';
|
||||||
import { textAlignmentProperty } from '../text-base';
|
import { textAlignmentProperty } from '../text-base';
|
||||||
@ -38,7 +38,7 @@ function initializeClickListener(): void {
|
|||||||
public onClick(v: android.view.View): void {
|
public onClick(v: android.view.View): void {
|
||||||
const owner = this.owner;
|
const owner = this.owner;
|
||||||
if (owner) {
|
if (owner) {
|
||||||
owner._emit(ButtonBase.tapEvent);
|
owner._emit(tapEvent);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -47,6 +47,9 @@ function initializeClickListener(): void {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export class Button extends ButtonBase {
|
export class Button extends ButtonBase {
|
||||||
|
// defining this here means tap event wont be handled
|
||||||
|
// by the gesture observers
|
||||||
|
public static tapEvent = tapEvent;
|
||||||
nativeViewProtected: android.widget.Button;
|
nativeViewProtected: android.widget.Button;
|
||||||
|
|
||||||
constructor() {
|
constructor() {
|
||||||
|
10
packages/core/ui/button/index.d.ts
vendored
10
packages/core/ui/button/index.d.ts
vendored
@ -1,14 +1,16 @@
|
|||||||
import { TextBase } from '../text-base';
|
import { TextBase } from '../text-base';
|
||||||
import { EventData } from '../../data/observable';
|
import { EventData } from '../../data/observable';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* String value used when hooking to tap event.
|
||||||
|
*/
|
||||||
|
export const tapEvent: string;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Represents a standard Button widget.
|
* Represents a standard Button widget.
|
||||||
*/
|
*/
|
||||||
export class Button extends TextBase {
|
export class Button extends TextBase {
|
||||||
/**
|
|
||||||
* String value used when hooking to tap event.
|
|
||||||
*/
|
|
||||||
public static tapEvent: string;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets the native [android widget](http://developer.android.com/reference/android/widget/Button.html) that represents the user interface for this component. Valid only when running on Android OS.
|
* Gets the native [android widget](http://developer.android.com/reference/android/widget/Button.html) that represents the user interface for this component. Valid only when running on Android OS.
|
||||||
|
@ -12,6 +12,8 @@ import { layout } from '../../utils';
|
|||||||
export * from './button-common';
|
export * from './button-common';
|
||||||
|
|
||||||
export class Button extends ButtonBase {
|
export class Button extends ButtonBase {
|
||||||
|
// we dont defile tapEvent to let the gesture obserers handle it
|
||||||
|
// in some weird case with UICollectionView UIControlEvents.TouchUpInside is not working
|
||||||
public nativeViewProtected: UIButton;
|
public nativeViewProtected: UIButton;
|
||||||
|
|
||||||
private _tapHandler: NSObject;
|
private _tapHandler: NSObject;
|
||||||
@ -21,18 +23,6 @@ export class Button extends ButtonBase {
|
|||||||
return UIButton.buttonWithType(UIButtonType.System);
|
return UIButton.buttonWithType(UIButtonType.System);
|
||||||
}
|
}
|
||||||
|
|
||||||
public initNativeView(): void {
|
|
||||||
super.initNativeView();
|
|
||||||
const nativeView = this.nativeViewProtected;
|
|
||||||
this._tapHandler = TapHandlerImpl.initWithOwner(new WeakRef(this));
|
|
||||||
nativeView.addTargetActionForControlEvents(this._tapHandler, 'tap', UIControlEvents.TouchUpInside);
|
|
||||||
}
|
|
||||||
|
|
||||||
public disposeNativeView(): void {
|
|
||||||
this._tapHandler = null;
|
|
||||||
super.disposeNativeView();
|
|
||||||
}
|
|
||||||
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
get ios() {
|
get ios() {
|
||||||
return this.nativeViewProtected;
|
return this.nativeViewProtected;
|
||||||
@ -266,27 +256,27 @@ export class Button extends ButtonBase {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@NativeClass
|
// @NativeClass
|
||||||
class TapHandlerImpl extends NSObject {
|
// class TapHandlerImpl extends NSObject {
|
||||||
private _owner: WeakRef<Button>;
|
// private _owner: WeakRef<Button>;
|
||||||
|
|
||||||
public static initWithOwner(owner: WeakRef<Button>): TapHandlerImpl {
|
// public static initWithOwner(owner: WeakRef<Button>): TapHandlerImpl {
|
||||||
const handler = <TapHandlerImpl>TapHandlerImpl.new();
|
// const handler = <TapHandlerImpl>TapHandlerImpl.new();
|
||||||
handler._owner = owner;
|
// handler._owner = owner;
|
||||||
return handler;
|
// return handler;
|
||||||
}
|
// }
|
||||||
|
|
||||||
public tap(args) {
|
// public tap(args) {
|
||||||
// _owner is a {N} view which could get destroyed when a tap initiates (protect!)
|
// // _owner is a {N} view which could get destroyed when a tap initiates (protect!)
|
||||||
if (this._owner) {
|
// if (this._owner) {
|
||||||
const owner = this._owner.get();
|
// const owner = this._owner.get();
|
||||||
if (owner) {
|
// if (owner) {
|
||||||
owner._emit(ButtonBase.tapEvent);
|
// owner._emit(ButtonBase.tapEvent);
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
|
|
||||||
public static ObjCExposedMethods = {
|
// public static ObjCExposedMethods = {
|
||||||
tap: { returns: interop.types.void, params: [interop.types.id] },
|
// tap: { returns: interop.types.void, params: [interop.types.id] },
|
||||||
};
|
// };
|
||||||
}
|
// }
|
||||||
|
@ -16,6 +16,8 @@ import { textTransformProperty, TextTransform } from '../../text-base';
|
|||||||
|
|
||||||
@CSSType('TabStripItem')
|
@CSSType('TabStripItem')
|
||||||
export class TabStripItem extends View implements TabStripItemDefinition, AddChildFromBuilder {
|
export class TabStripItem extends View implements TabStripItemDefinition, AddChildFromBuilder {
|
||||||
|
// defining this here means tap event wont be handled
|
||||||
|
// by the gesture observers
|
||||||
public static tapEvent = 'tap';
|
public static tapEvent = 'tap';
|
||||||
public static selectEvent = 'select';
|
public static selectEvent = 'select';
|
||||||
public static unselectEvent = 'unselect';
|
public static unselectEvent = 'unselect';
|
||||||
|
Reference in New Issue
Block a user