@@ -39,10 +39,10 @@ export default function StreamCanvas({ deviceData }) {
39
39
40
40
let streamUrl = ""
41
41
if ( deviceData . os === 'ios' ) {
42
- // streamUrl = `http://192.168.1.6 :10000/device/${deviceData.udid}/ios-stream-mjpeg`
42
+ // streamUrl = `http://192.168.1.41 :10000/device/${deviceData.udid}/ios-stream-mjpeg`
43
43
streamUrl = `/device/${ deviceData . udid } /ios-stream-mjpeg`
44
44
} else {
45
- // streamUrl = `http://192.168.1.6 :10000/device/${deviceData.udid}/android-stream-mjpeg`
45
+ // streamUrl = `http://192.168.1.41 :10000/device/${deviceData.udid}/android-stream-mjpeg`
46
46
streamUrl = `/device/${ deviceData . udid } /android-stream-mjpeg`
47
47
}
48
48
@@ -224,47 +224,28 @@ export default function StreamCanvas({ deviceData }) {
224
224
225
225
function Canvas ( { authToken, logout, streamData, setDialog } ) {
226
226
var tapStartAt = 0
227
- var coord1 ;
228
- var coord2 ;
227
+ var coord1
228
+ var coord2
229
229
230
230
function getCursorCoordinates ( event ) {
231
231
const rect = event . currentTarget . getBoundingClientRect ( )
232
- // If its portrait use the usual calculation for tap coordinates
233
- if ( streamData . isPortrait ) {
234
- const x = event . clientX - rect . left
235
- const y = event . clientY - rect . top
236
- return [ x , y ]
237
- }
238
- // If its landscape and the provider uses custom wda for tapping/swiping
239
- if ( streamData . device_os === 'ios' && streamData . uses_custom_wda ) {
240
- // Have to subtract the tap coordinate from the canvas height
241
- // Because the custom wda tap uses coordinates where in landscape
242
- // x starts from the bottom(being essentially reversed y)
243
- // and y starts from the left(being essentially x)
244
- const x = streamData . canvasHeight - ( event . clientY - rect . top )
245
- const y = event . clientX - rect . left
246
- return [ x , y ]
247
- }
248
- // If its landscape and provider does not use custom wda for tapping/swiping
249
- // just reverse x and y
250
- const x = event . clientY - rect . top
251
- const y = event . clientX - rect . left
252
- console . log ( "Returning " + x + " " + y )
253
- return [ y , x ] ;
232
+ const x = event . clientX - rect . left
233
+ const y = event . clientY - rect . top
234
+ return [ x , y ] ;
254
235
}
255
236
256
237
function handleMouseDown ( event ) {
257
238
tapStartAt = ( new Date ( ) ) . getTime ( )
258
239
coord1 = getCursorCoordinates ( event )
259
- console . log ( 'Tapped on ' + coord1 )
260
240
}
261
241
262
242
function handleMouseUp ( event ) {
263
243
coord2 = getCursorCoordinates ( event )
264
- console . log ( 'Released on' + coord2 )
265
244
// get the time of finishing the click on the canvas
266
245
var tapEndAt = ( new Date ( ) ) . getTime ( )
267
246
247
+ console . log ( 'Tap on ' + coord1 [ 0 ] + 'x' + coord1 [ 1 ] + ', released on ' + coord2 [ 0 ] + 'x' + coord2 [ 1 ] )
248
+
268
249
var mouseEventsTimeDiff = tapEndAt - tapStartAt
269
250
270
251
// if the difference of time between click down and click up is more than 500ms assume it is a swipe, not a tap
@@ -275,7 +256,7 @@ function Canvas({ authToken, logout, streamData, setDialog }) {
275
256
// if x2 < x1*0.9 - it is probably a swipe right to left
276
257
// if y2 < y1*0.9 - it is probably a swipe bottom to top
277
258
// if y2 > y1*1.1 - it is probably a swipe top to bottom
278
- if ( mouseEventsTimeDiff > 500 || coord2 [ 0 ] > coord1 [ 0 ] * 1.1 || coord2 [ 0 ] < coord1 [ 0 ] * 0.9 || coord2 [ 1 ] < coord1 [ 1 ] * 0.9 || coord2 [ 1 ] > coord1 [ 1 ] * 1.1 ) {
259
+ if ( mouseEventsTimeDiff > 500 && coord2 [ 0 ] > coord1 [ 0 ] * 1.1 || coord2 [ 0 ] < coord1 [ 0 ] * 0.9 || coord2 [ 1 ] < coord1 [ 1 ] * 0.9 || coord2 [ 1 ] > coord1 [ 1 ] * 1.1 ) {
279
260
swipeCoordinates ( authToken , logout , coord1 , coord2 , streamData , setDialog )
280
261
} else if ( mouseEventsTimeDiff < 500 ) {
281
262
tapCoordinates ( authToken , logout , coord1 , streamData , setDialog )
@@ -314,20 +295,33 @@ function tapCoordinates(authToken, logout, pos, streamData, setDialog) {
314
295
let x = pos [ 0 ]
315
296
let y = pos [ 1 ]
316
297
317
- // if the stream height
318
- if ( streamData . canvasHeight != streamData . deviceY ) {
319
- if ( streamData . isPortrait ) {
320
- x = ( x / streamData . canvasWidth ) * streamData . deviceX
321
- y = ( y / streamData . canvasHeight ) * streamData . deviceY
322
- } else {
323
- x = ( x / streamData . canvasHeight ) * streamData . deviceX
324
- y = ( y / streamData . canvasWidth ) * streamData . deviceY
298
+ let finalX = ( x / streamData . canvasWidth ) * streamData . deviceX
299
+ let finalY = ( y / streamData . canvasHeight ) * streamData . deviceY
300
+ // If its portrait we keep the x and y as is
301
+ if ( ! streamData . isPortrait ) {
302
+ // If its landscape
303
+ // And its Android we still keep the x and y as is because for Android Appium does the coordinates are actually corresponding to the view
304
+ // If we are in portrait X is X and Y is Y and when we are in landscape its the same
305
+ if ( streamData . device_os === 'android' ) {
306
+ finalX = ( x / streamData . canvasHeight ) * streamData . deviceX
307
+ finalY = ( y / streamData . canvasWidth ) * streamData . deviceY
308
+ }
309
+ if ( streamData . device_os === 'ios' ) {
310
+ if ( streamData . uses_custom_wda ) {
311
+ finalX = streamData . deviceX - ( ( y / streamData . canvasHeight ) * streamData . deviceX )
312
+ finalY = ( x / streamData . canvasWidth ) * streamData . deviceY
313
+ } else {
314
+ // On normal WDA in landscape X corresponds to the canvas width but it is actually the device's height
315
+ finalX = ( x / streamData . canvasWidth ) * streamData . deviceY
316
+ // Y corresponds to the canvas height but it is actually the device's width
317
+ finalY = ( y / streamData . canvasHeight ) * streamData . deviceX
318
+ }
325
319
}
326
320
}
327
321
328
322
let jsonData = JSON . stringify ( {
329
- "x" : x ,
330
- "y" : y
323
+ "x" : finalX ,
324
+ "y" : finalY
331
325
} )
332
326
333
327
let deviceURL = `/device/${ streamData . udid } `
@@ -353,15 +347,34 @@ function touchAndHoldCoordinates(authToken, logout, pos, streamData, setDialog)
353
347
let x = pos [ 0 ]
354
348
let y = pos [ 1 ]
355
349
356
- // if the stream height
357
- if ( streamData . canvasHeight != streamData . deviceY ) {
358
- x = ( x / streamData . canvasWidth ) * streamData . deviceX
359
- y = ( y / streamData . canvasHeight ) * streamData . deviceY
350
+ let finalX = ( x / streamData . canvasWidth ) * streamData . deviceX
351
+ let finalY = ( y / streamData . canvasHeight ) * streamData . deviceY
352
+
353
+ // If its portrait we keep the x and y as is
354
+ if ( ! streamData . isPortrait ) {
355
+ // If its landscape
356
+ // And its Android we still keep the x and y as is because for Android Appium does the coordinates are actually corresponding to the view
357
+ // If we are in portrait X is X and Y is Y and when we are in landscape its the same
358
+ if ( streamData . device_os === 'android' ) {
359
+ finalX = ( x / streamData . canvasHeight ) * streamData . deviceX
360
+ finalY = ( y / streamData . canvasWidth ) * streamData . deviceY
361
+ }
362
+ if ( streamData . device_os === 'ios' ) {
363
+ if ( streamData . uses_custom_wda ) {
364
+ finalX = streamData . deviceX - ( ( y / streamData . canvasHeight ) * streamData . deviceX )
365
+ finalY = ( x / streamData . canvasWidth ) * streamData . deviceY
366
+ } else {
367
+ // On normal WDA in landscape X corresponds to the canvas width but it is actually the device's height
368
+ finalX = ( x / streamData . canvasWidth ) * streamData . deviceY
369
+ // Y corresponds to the canvas height but it is actually the device's width
370
+ finalY = ( y / streamData . canvasHeight ) * streamData . deviceX
371
+ }
372
+ }
360
373
}
361
374
362
375
let jsonData = JSON . stringify ( {
363
- "x" : x ,
364
- "y" : y
376
+ "x" : finalX ,
377
+ "y" : finalY
365
378
} )
366
379
367
380
let deviceURL = `/device/${ streamData . udid } `
@@ -388,31 +401,66 @@ function swipeCoordinates(authToken, logout, coord1, coord2, streamData, setDial
388
401
var secondCoordX = coord2 [ 0 ]
389
402
var secondCoordY = coord2 [ 1 ]
390
403
391
- // if the stream height
392
- if ( streamData . canvasHeight != streamData . deviceY ) {
393
- // If the device is landscape and is android
394
- // We need to switch the coordinate calculation
395
- // Divide by height for X and divide by width for Y
396
- if ( streamData . device_os === 'android' && ! streamData . isPortrait ) {
397
- firstCoordX = ( firstCoordX / streamData . canvasHeight ) * streamData . deviceX
398
- firstCoordY = ( firstCoordY / streamData . canvasWidth ) * streamData . deviceY
399
- secondCoordX = ( secondCoordX / streamData . canvasHeight ) * streamData . deviceX
400
- secondCoordY = ( secondCoordY / streamData . canvasWidth ) * streamData . deviceY
404
+ // Set up the portrait tap coordinates
405
+ // We divide the current coordinate by the canvas size to get the ratio
406
+ // Then we multiply by the actual device width or height to get the actual coordinates on the device that we should send
407
+ let firstXFinal = ( firstCoordX / streamData . canvasWidth ) * streamData . deviceX
408
+ let firstYFinal = ( firstCoordY / streamData . canvasHeight ) * streamData . deviceY
409
+ let secondXFinal = ( secondCoordX / streamData . canvasWidth ) * streamData . deviceX
410
+ let secondYFinal = ( secondCoordY / streamData . canvasHeight ) * streamData . deviceY
411
+
412
+ // If in landscape we need to do different recalculations
413
+ if ( ! streamData . isPortrait ) {
414
+ // If the device is android we just reverse the calculations
415
+ // For X we divide the coordinate by the canvas height to get the correct ratio
416
+ // And for Y we divide the coordinate by the canvas width to get the correct ratio
417
+ // Multiplication is the same as for portrait because Appium for Android follows some actual logic
418
+ if ( streamData . device_os === 'android' ) {
419
+ firstXFinal = ( firstCoordX / streamData . canvasHeight ) * streamData . deviceX
420
+ firstYFinal = ( firstCoordY / streamData . canvasWidth ) * streamData . deviceY
421
+ secondXFinal = ( secondCoordX / streamData . canvasHeight ) * streamData . deviceX
422
+ secondYFinal = ( secondCoordY / streamData . canvasWidth ) * streamData . deviceY
401
423
} else {
402
- // If the device is not in landscape and is not android
403
- // Divide as usual - X by width and Y by height
404
- firstCoordX = ( firstCoordX / streamData . canvasWidth ) * streamData . deviceX
405
- firstCoordY = ( firstCoordY / streamData . canvasHeight ) * streamData . deviceY
406
- secondCoordX = ( secondCoordX / streamData . canvasWidth ) * streamData . deviceX
407
- secondCoordY = ( secondCoordY / streamData . canvasHeight ) * streamData . deviceY
424
+ // For iOS its complete sh*t
425
+ if ( streamData . uses_custom_wda ) {
426
+ // NB: All calculations below are when the device is on its right side landscape(your left)
427
+ // For custom WDA the 0 X coordinate is at the bottom of the canvas
428
+ // And the 0 Y coordinate is at the left end of the canvas
429
+ // This means that they kinda follow the portrait logic but inverted based on the side it is in landscape
430
+ // Imagine a device that is X:Y=100:200
431
+ // If you swipe vertically from bottom to the middle you are essentially swiping coordinates on the device X:0 and X: 50
432
+ // And if you swipe horizontally from left to middle you are essentially swiping coordinates on the device Y: 0 and Y: 100
433
+ // But on the canvas those are Y coordinates
434
+ // And this is where it gets funky
435
+ // For X we get the ratio from the canvas Y coordinate and the canvas height
436
+ // And we multiply it by the device width because that is what it corresponds to
437
+ // Then we subtract the value from the actual deviceX because the device width starts from the bottom of the canvas height
438
+ firstXFinal = streamData . deviceX - ( ( firstCoordY / streamData . canvasHeight ) * streamData . deviceX )
439
+ // For Y we get the ratio from the canvas X coordinate and the canvas width
440
+ // And we multiply it by the device height because that is what it corresponds to
441
+ firstYFinal = ( firstCoordX / streamData . canvasWidth ) * streamData . deviceY
442
+ // Same goes for the other two coordinates when the mouse is released
443
+ secondXFinal = streamData . deviceX - ( ( secondCoordY / streamData . canvasHeight ) * streamData . deviceX )
444
+ secondYFinal = ( secondCoordX / streamData . canvasWidth ) * streamData . deviceY
445
+ } else {
446
+ // On normal WDA the X coordinates correspond to the device height
447
+ // and the Y coordinates correspond to the device width
448
+ // So we calculate ratio based on canvas dimensions and coordinates
449
+ // But multiply by device height for X swipe coordinates and by device width for Y swipe coordinates
450
+ firstXFinal = ( firstCoordX / streamData . canvasWidth ) * streamData . deviceY
451
+ firstYFinal = ( firstCoordY / streamData . canvasHeight ) * streamData . deviceX
452
+ secondXFinal = ( secondCoordX / streamData . canvasWidth ) * streamData . deviceY
453
+ secondYFinal = ( secondCoordY / streamData . canvasHeight ) * streamData . deviceX
454
+ }
408
455
}
409
456
}
457
+ console . log ( 'Swipe is ' + firstXFinal + ':' + firstYFinal + '-' + secondXFinal + ':' + secondYFinal )
410
458
411
459
let jsonData = JSON . stringify ( {
412
- "x" : firstCoordX ,
413
- "y" : firstCoordY ,
414
- "endX" : secondCoordX ,
415
- "endY" : secondCoordY
460
+ "x" : firstXFinal ,
461
+ "y" : firstYFinal ,
462
+ "endX" : secondXFinal ,
463
+ "endY" : secondYFinal
416
464
} )
417
465
418
466
let deviceURL = `/device/${ streamData . udid } `
0 commit comments