I´m trying to implement a canvas element to touch sign in Safari/iPad. I have done it for desktop browsers with mousedown mouseup and mousemove events. Which events I have to use for do the same in iPad? touchstart,touchend and touchmove?
here is my function
var pizarra_canvas
var pizarra_context
function init(){
alert('2')
pizarra_canvas = document.getElementById("pizarra");
pizarra_context = pizarra_canvas.getContext("2d");
pizarra_context.strokeStyle = "#000";
pizarra_canvas.addEventListener('touchstart',empezarPintar,false);
pizarra_canvas.addEventListener('touchend',terminarPintar,false);
alert('1')
}
function empezarPintar(e){
pizarra_context.beginPath();
pizarra_context.moveTo(e.clientX-pizarra_canvas.offsetLeft,e.clientY- pizarra_canvas.offsetTop);
pizarra_canvas.addEventListener('touchmove',pintar,false)
}
function terminarPintar(e){
pizarra_canvas.removeEventListener('touchmove',pintar,false);
}
function pintar(e) {
pizarra_context.lineTo(e.clientX-pizarra_canvas.offsetLeft,e.clientY- pizarra_canvas.offsetTop);
pizarra_context.stroke();
}
I advise you to have a look at frameworks like http://www.kineticjs.com/ or http://paperjs.org/ which help a lot when dealing with canvas on a touch-screen.
Related
I am using fabricjs for canvas and hammerjs for touch event with Angular 9. I have a single tap event of hammerjs which creates an object of fabric's IText. Single tapping creates the fabric and populates it on the canvas, but the device keyboard does not open to add text in the text object. The fabricjs's IText creates TEXTAREA internally to allow text entering.
Tried with:
1. canvas.getActiveObject().enterEditing();
canvas.getActiveObject().hiddenTextarea.focus();
2. document.querySelector('[data-fabric-hiddentextarea]').setAttribute("autofocus", "");
document.querySelector('[data-fabric-hiddentextarea]').focus();
document.querySelector('[data-fabric-hiddentextarea]').click();
Above solutions were tried with settimeout as well.
Please suggest.
thanks in advance
Found a way by using VanilaJS touchend event. Had to remove the HammerJS's doubletap event and use touchend event.
let element = document.getElementById('canvasId');
let timedout;
let lastTaped = 0;
element.addEventListener('touchend', (event) => {
var currentTime = new Date().getTime();
var tapLength = currentTime - lastTaped;
clearTimeout(timedout);
if (tapLength < 500 && tapLength > 0) {
// code to add the iText object
event.preventDefault();
}
lastTaped = currentTime;
}
});
thanks :) keep coding
Please note that this question is for Cordova/PhoneGap/Hybrid apps.
I have a <textarea> for which I want the app to behave in a certain way only when voice dictation input has ended -- i.e. user tabs "Done". However, this is proving to be rather difficult.
iOS's UIKit provides dictationRecordingDidEnd event under UITextInput but I am not sure if this can even be used in a hybrid app. (iOS Developer Library doc here)
EDIT: I am using ionic-plugin-keyboard.
Any ideas would be greatly appreciated.
Maybe you can try to use the SpeechRecognitionPlugin or cordova-plugin-iflyspeech
For the cordova-plugin-iflyspeech you have 13 events to have control of the voice control in your iOS device like:
SpeechBegin
SpeechEnd
SpeechCancel
SpeechResults
SpeechError
VolumeChanged
SpeakBegin
SpeakPaused
SpeakResumed
SpeakCancel
SpeakCompleted
SpeakProgress
BufferProgress
And has support for a big number of languages like: English (US), English (UK), French, Spanish, Italian, etc.
This is an example of the documentation
function onLoad() {
document.addEventListener("deviceready", onDeviceReady, false);
}
function onDeviceReady() {
$('div#status').html( 'speech engine ready' );
}
function startReading() {
var text = $('textarea#read').val();
navigator.speech.startSpeaking( text, {voice_name: 'xiaoyan'} );
}
function stopReading() {
navigator.speech.stopSpeaking();
}
function startListening() {
$('div#status').html( 'Listening, please speak.' );
navigator.speech.startListening({language:'en-US'} function(str) {
// this is what the device hear and understand
$('textarea#read').val( str );
});
}
function stopListening() {
navigator.speech.stopListening();
}
And here you can bind the iOS method dictationRecordingDidEnd to:
stopListening(); or cancelListening(); methods, depending the action.
I have an OpenLayers 3.9.0 map. I also have a pair of LonLat coordinates that I am tracking from an external source and updating onto the map. I am continuously re-centering the map on these coordinates:
function gets_called_when_I_have_updated_coords() {
map.getView.setCenter(coords);
}
What I want is to disable this auto-centering whenever the user interacts with the map. In other words, I want this:
var auto_center = true;
function gets_called_when_I_have_updated_coords() {
if (auto_center) {
map.getView.setCenter(coords);
}
}
function user_started_interacting() {
auto_center = false;
}
// But where should this function be attached to?
// where.on('what?', user_started_interacting);
I don't know how to detect a user interaction.
I expected that the default interactions had some kind of event, so that when the user starts dragging/rotating/zooming the map, an event would be triggered and my code would run. I could not find such event.
Here, the user is dragging:
map.on('pointermove', function(evt){
if(evt.dragging){
//user interacting
console.info('dragging');
}
});
Here, the user is changing resolution:
map.getView().on('change:resolution', function(evt){
console.info(evt);
});
UPDATE
Some options to detect keyboard interaction:
//unofficial && undocumented
map.on('key', function(evt){
console.info(evt);
console.info(evt.originalEvent.keyIdentifier);
});
//DOM listener
map.getTargetElement().addEventListener('keydown', function(evt){
console.info(evt);
console.info(evt.keyIdentifier);
});
A fiddle to test.
An other approach could be to listen to the pointerdown and pointerup events occurring on the map and while the down is in action, disable your auto-center feature.
map.on('pointerdown', function() {
auto_center = false;
}, this);
map.on('pointerup', function() {
auto_center = true;
}, this);
This approach may need more work, but it would be a start. Thoughts ?
As an workaround, I can attach an event to a change in the view:
map.getView().on('change:center', function(ev){…});
But I must take extra steps to distinguish from code-initiated changes from user-initiated ones. The complete code looks somewhat like this:
var auto_center = true;
var ignore_change_events = false;
function gets_called_when_I_have_updated_coords() {
if (auto_center) {
ignore_change_events = true;
map.getView.setCenter(coords);
ignore_change_events = false;
}
}
map.getView().on('change:center', function() {
if (ignore_change_events) {
return;
}
auto_center = false;
});
Note that this approach breaks if any animation is used (and there is no callback or event for when an animation finishes).
Depending on your project, you may want to try either this solution or Jonatas Walker's solution.
So only in safari on the ipad I am having an issue with the play/pause not firing inside a setTimeout. This works in all browsers and even in safari on PC and Mac, just not on ipad. If I take the setTimeout it works, but I need the setTimeout.
This is for JWPlayer 5.9.2156
jwplayer("Container").setup({
events: {
onBeforePlay: function () {
jwplayer("Container").pause('true');
if(tOut) {
clearTimeout(tOut);
tOut = null;
}
var tOut = setTimeout($.proxy(function () {
jwplayer("Container").pause("false"); //this doesnt happen
console.log("this happens");
}.bind(this), this), 1000);
},
onPause: function (e) {
//this isnt firing
console.log("OnPause fired: "+e.oldstate);
}
...
While this may not be on the same topic at first glance the accepted answer given here also applies to this situation.
HTML5 audio object doesn't play on iPad (when called from a setTimeout)
I am using wall.plasm.it and would like to use slimbox to open the images in fullscreen http://www.digitalia.be/software/slimbox
But when I add the slimbox script to my website and click on an image, it just opens the image and redirects me to the image on the server but doesnt start slimbox
Ah, so it seems you would have to do something like the following:
Use wall.setCallOnUpdate( myFunctionUpdate ); (this) to update all newly generated images so that they have the rel=lightbox attribute set.
Reinitialize slimbox.
--OR--
You could simply use the CallOnUpdate to directly enable the slimbox on items using the API
I think you need to use Event Delegation - this is how I got my wall working with lightbox. I called this after the initWall() method and also the changeOnUpdate() so the new events would be added.
var boundClicker;
$$('div.tile a').each(function(button) {
var linkDest = button.get('href');
var title = button.get('data-title');
var type = button.get('rel');
var clicker = function(event)
{
event.stop();
Mediabox.open(linkDest, title, '470 290');
};
boundClicker = clicker.bind(button);
button.addEvent('click', boundClicker);
});
Add a "click" event handler and use the getMovement function.
items.each(function(item) {
item.addEvent("click",function(e){
if( wall.getMovement() ){
e.stop();
}
else {
Mediabox.open(...);
}
}); }