how to implement long touch in titanium - android

I am working at an Android app in Titanium. My question is how to implement long touch in Titanium? I need something like this: when user keep pressed a certain view to call some function. I tried this :
arrowright.addEventListener('touchstart', function(e) {
touched = true;
setTimeout(function() {
if (touched) {
arrowright.fireEvent('longTouch');
}
},100);
});
arrowright.addEventListener('touchmove', function(e) {
touched = false;
});
arrowright.addEventListener('touchend', function(e) {
touched = false;
});
arrowright.addEventListener('longTouch',function(){
clickTheView(e);
},
false);
but this is not working like I want. My function clickTheView(e) is call every time I click the view and it is not called when I touch for a long time the view.
Any idea is welcome. Thanks in advance.

If you have the latest Ti SDK its included. See http://developer.appcelerator.com/apidoc/mobile/latest/Titanium.UI.Button.longpress-event.html

Related

Overriding back button in sencha app for Android

While using a sencha touch app on Android, is it possible that the device back button behaves completely as it behaves for a native Andriod app? This thread addresses the same problem. The suggested solution is
if (Ext.os.is('Android')) {
document.addEventListener("backbutton", Ext.bind(onBackKeyDown, this), false);
function onBackKeyDown(eve) {
eve.preventDefault();
//do something
alert('back button pressed');
}
}
but in this function, how can i go to the previously visited screen?
Of course it depends on how your user interface is built and how the views are connected. Simplest way I can think of is to detect somehow the presence of a back button in the page and trigger a click on it.
In my application each view that needs to handle the backbutton event has a button with cls = 'back' that implements a tap listener responsible of the logic to go back to the previous view.
About how to implement this logic: there is no magic wand for that. If a particular view can be reached through one and only one parent view, then you can hardcode it. Else, if a view can be reached from more than one, I save in a property of the view's controller a reference to the view which I came from, and then on backbutton's tap I move to that view.
The animation of moving to a view can usually be obtained by Ext.Viewport.animateActiveItem(parentView, {type: 'fade'}); (but again it depends on how you implemented your views tree)
So in my handler for the backbutton I check for such a button with [cls=back] (but you could also check for ui or whatever you want) and I fire the tap event on it.
Moreover, when i detect I am on the root view I ask the user if he wants to exit the application and if so I call exit().
_handleBackButtonEvent : function(e) {
// First look if the current view is the mainView
var item = Ext.Viewport.getActiveItem();
// If we are on mainView, quit.
// Sayonara, goodbye, adios
if (item.getId() === 'mainView') {
navigator.notification.confirm(
"Really quit?",
function(option) {
if (option == 1) {
navigator.app.exitApp();
}
},
"Confirm",
"Yes,No"
);
} else {
// else look if the current view has a backbutton
var titlebar = item.down('titlebar[docked=top]');
var backbutton = null;
if (titlebar) {
backbutton = titlebar.down('button[iconCls=back]');
}
if (backbutton && !backbutton.isHidden() && !backbutton.isDisabled()) {
backbutton.fireEvent('tap');
} else {
// if not, fallback to mainView
item = Ext.getCmp('mainView');
Ext.Viewport.animateActiveItem( item, {type: 'slide', direction: 'right'});
}
}
e.preventDefault();
}

Make :hover on Android require two clicks to open a link

I've built a great, responsive CSS navigation, but I'm having trouble getting it to work in Android without jQuery. In iOS and Windows Phone, when the user taps on a navigation link that has drop downs, the drop down expands. If the user taps on this link a second time, they get taken to that link.
Is there anything similar I can do for Android? Or am I stuck using jQuery?
Example URL: http://bearce.me/nav
Alright< I figured this out. Sadly, there's no way to do it with CSS. I ended up writing some JavaScript that detects if it's Android, and if so, triggers the drop downs in a touch-friendly way. Here's the code, for anyone who's curious:
// fixes drop downs in Android
if (navigator.userAgent.toLowerCase().indexOf("android") > -1) {
$(document).ready(function() {
// fixes drop downs
$("nav ul li ul, nav ul li ul li ul").parent("li").children("a").each(function() {
var touched = false;
$(this).click(function(e) {
if (touched == true) {
} else {
e.preventDefault();
$(this).next("ul").trigger("mouseenter");
touched = true;
}
});
$(this).mouseleave(function() {
touched = false;
});
});
// fixes menu button
$("nav > a").each(function() {
var touched = false;
$(this).click(function(e) {
e.preventDefault();
if (touched == true) {
$(this).next("ul").trigger("mouseleave");
touched = false;
} else {
$(this).next("ul").trigger("mouseenter");
touched = true;
}
});
});
});
}

Disable long click in android webview

I am using css columns to display contents in android webview. I used longclicklistner {return true}; with this I was able to disable longclick in phones but it doesn't seem to work in tabs(eg galaxy tab 2). I'm also preventing touchmove event using jquery but the css columns are moving when swipe occurs as part of longclick. Any help is welcome. Thank you.
wbView.setOnLongClickListener(new View.OnLongClickListener() {
#Override
public boolean onLongClick(View v) {
return true;
}
});
wbView.setLongClickable(false);
jquery code:
document.getElementById("divIdToShowContent").ontouchmove = function(e){
e.preventDefault();
var touching = null;
}
You have to use a GestureDetector, the SimpleOnGestureListener has onSingleTapConfirmed() for click events and onFling() for swipe events.
Refer this
I avoided using GestureDetector and SimpleOnGestureListener, I done it with catching touch listnerby catching the position fron MotionEvent.ACTION_DOWN and MotionEvent.ACTION_UP
Try this :
_webview.setOnLongClickListener(new OnLongClickListener() {
#Override
public boolean onLongClick(View v) {
return true;
}
});

Detect touch event outside of layout

I'm using an opensource numberpicker I found somewhere (credit to Jeffrey F. Cole) but I just found a bug.
The numberpicker has a handler to increase the number faster when you touch the button
long`private Handler repeatUpdateHandler = new Handler();
`
class RepetetiveUpdater implements Runnable {
public void run() {
if (autoIncrement) {
increment();
repeatUpdateHandler.postDelayed(new RepetetiveUpdater(),
REPEAT_DELAY);
} else if (autoDecrement) {
decrement();
repeatUpdateHandler.postDelayed(new RepetetiveUpdater(),
REPEAT_DELAY);
}
}
}
.....
public class NumberPicker extends LinearLayout {
.....
// Auto increment for a long click
increment.setOnLongClickListener(new View.OnLongClickListener() {
public boolean onLongClick(View arg0) {
autoIncrement = true;
repeatUpdateHandler.post(new RepetetiveUpdater());
return false;
}
});
// When the button is released, if we're auto incrementing, stop
increment.setOnTouchListener(new View.OnTouchListener() {
public boolean onTouch(View v, MotionEvent event) {
if (event.getAction() == MotionEvent.ACTION_UP && autoIncrement) {
autoIncrement = false;
}
return false;
}
});
The problem is when you longclick the button the counter starts to increase, but when you hold your finger down and drag your finger across the screen the counter keeps adding up, even when you lift your finger.
So how can I detect that the finger gets out of my numberpicker layout and stop the counter?
Thx :)
I'm not so sure that's a bug and I'm not even sure it's coming from changes that this number picker made on top of the numberpicker from the API itself. I'm assumings that the buttons that handles incrementing and decrementing the pickers are set up to keep going until an ACTION_UP MotionEvent is received, but this might be over-simplifying it.
EDIT:
I've tested this on stock Android 2.3.3 and this is precisely the result.
EDIT:
Based on your clarification in the comments, this does sound like a pretty bad bug. Looks like what you need to do is have the Handler removes the callbacks to that runnable in ACTION_UP. Can you link me to the project so I can try to submit a patch?
EDIT
The NumberPicker you provided wasn't using Handlers correctly, IMO. Instead of keeping a reference to the same Handler so that callbacks could later be removed, it was created a new one everytime it posted. I've made some changes and fixed the issues here: https://gist.github.com/3657989

setVisibilty() wont work first time

I have a layout called a controller in it i have a couple buttons and such
the problem is in my onTouch function i want to show it on one click and hide it on another. Now this works after 2 touches. The first touch is supposed to show the controller while the next is supposed to make it disappear. The first and second touches do nothing but on the third touch it works. Here are the related functions for this
public boolean onTouchEvent(MotionEvent event)
{
int eventx = event.getAction();
switch(eventx)
{
case MotionEvent.ACTION_DOWN:
if(isLifted)
{
if(!isVisible)
{
Log.i("onTouch", "called showPuse menu");
isVisible = true;
isPaused = true;
showPauseMenu();
}
else if(isVisible)
{
hidePauseMenu();
isVisible= false;
}
isLifted = false;
}
break;
case MotionEvent.ACTION_UP:
if(!isLifted)
{
isLifted = true;
//Log.i("onTouchEvent", "Lifted");
}
}
return false;
}
/***************************************************
* Shows All Views needed to be shown
* Also pauses video and audio
*
* *************************************************/
private void showPauseMenu()
{
Log.i("showPauseMenu", "called");
playButton.setVisibility(View.VISIBLE);
Log.i("showPauseMenu", "plaButton visible");
bottomButtons.setVisibility(View.VISIBLE);
Log.i("showPauseMenu", "bottom Menu showed");
playButton.invalidate();
bottomButtons.invalidate();
pauseMedia();
}
/************************************************
* Hides Views that are part of Pause Menu
* Also starts video and audio back again
*/
private void hidePauseMenu() {
playButton.setVisibility(View.GONE);
bottomButtons.setVisibility(View.GONE);
playMedia();
}
Can anyone say what the problem might be? I've been looking at this code for a couple of days now and cant see what it might be.
A few pointers about this code:
The isLifted variable presumably starts out false, and on the first touch event it causes nothing to happen on the down event. When the user lifts his/her finger the variable is set to true so the second event can actually be processed. This means the first touch will never have any visible effect.
You're using an isVisible boolean instead of just checking the visibility of the components themselves. This makes it very easy to get them out of sync.
Without the full class it's hard to tell, but I'd investigate both these points.
While designing the xml make the widget android:visibility="gone". During the program check the state if its hidden onclick set View.VISIBLE and if visible on second touchView.GONE.
I think this will work. Try it once.

Categories

Resources