xpra-org / xpra-html5 Goto Github PK
View Code? Open in Web Editor NEWHTML5 client for Xpra
License: Mozilla Public License 2.0
HTML5 client for Xpra
License: Mozilla Public License 2.0
Issue migrated from trac ticket # 1844
component: html5 | priority: critical | resolution: fixed
See Unblocking Clipboard Access: It's a replacement for execCommand-based copy & paste that has a well-defined permissions model and doesn't block the page.
MDN: Navigator clipboard.
Original html5 clipboard tickets: Xpra-org/xpra#842, Xpra-org/xpra#1461
Could be useful for debugging rendering issues.
See Canvas toBlob() Support and Using HTML5/Canvas/JavaScript to take in-browser screenshots
Split from Xpra-org/xpra#2231, see Xpra-org/xpra#2231#comment:9.
Damage latency goes up to 7 seconds with chrome!
Average is also too high.
This would allow us to:
API Pointers:
Just like Xpra-org/xpra#2170 but for yuicompressor.
Issue migrated from trac ticket # 2123
component: html5 | priority: trivial | resolution: fixed
I got error if want to use Xpra html5 inside iframe element:
Uncaught DOMException: Failed to read the 'sessionStorage' property from 'Window': Access is denied for this document.Browser stopped, nothing to see. It appears in file 'Utilities.js', about in 436 line. If I catch error then everything works normally. So, the modification looks:
var value = getParameter(prop); try { if (value === undefined && typeof(sessionStorage) !== undefined) value = sessionStorage.getItem(prop); } catch (e) { // nothig to catch } return value;
I use Debian Stretch packages for version 2.4.3.
The window gets repainted with the updated contents (new size), but then somehow ends up being repainted again with empty contents (white).
Debug paint log:
client draw may_paint_now() paint pending= 0 , paint queue length= 1
client draw do_paint( 2388 bytes of webp data 775 x 927 at 0 , 0 ) focused= true
client draw request_redraw for Window(1)
client draw swap_buffers
client draw decode time for webp sequence 21 : 5 , flush= 0
client draw may_paint_now() paint pending= 0 , paint queue length= 0
client draw animation frame: 1 windows to paint
in an xterm, select a word with a double click, the use middle click to paste it.
With all other browsers, the word is pasted into the xterm once, with IE it gets pasted twice!
Double click on the word ADDRCONF
, previous value was NETDEV_CHANGE
:
28,766 client 5 clipboard paste event, data= NETDEV_CHANGE
28,767 process_button_action(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), [b'button-action', 1, 1, 1, [504, 248], [], []])
28,769 do_process_mouse_common(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), 1, [504, 248], -1)
28,770 move_pointer(1, [504, 248], -1) screen_no=-1, device=XTestPointerDevice, position=(504, 248)
28,770 xtest_fake_motion(-1, 504, 248)
28,771 xtest_fake_button(1, 1)
28,796 compress: 0.6ms for 78x13 pixels at 203,119 for wid=1 using rgb24 with ratio 16.9% ( 3KB to 0KB), sequence 43, client_options={'rgb_format': 'RGB', 'lz4': 1, 'flush': 1}
28,797 compress: 0.4ms for 6x13 pixels at 185,301 for wid=1 using rgb24 with ratio 75.0% ( 0KB to 0KB), sequence 44, client_options={'rgb_format': 'RGB'}
28,827 client 5 clipboard paste event, data= NETDEV_CHANGE
28,828 client 5 clipboard paste event, data= NETDEV_CHANGE
28,828 client 5 clipboard pending= false buffer= NETDEV_CHANGE
28,828 process_button_action(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), [b'button-action', 1, 1, 0, [504, 248], [], []])
28,829 do_process_mouse_common(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), 1, [504, 248], -1)
28,829 move_pointer(1, [504, 248], -1) screen_no=-1, device=XTestPointerDevice, position=(504, 248)
28,829 xtest_fake_motion(-1, 504, 248)
28,829 xtest_fake_button(1, 0)
28,851 compress: 0.1ms for 6x13 pixels at 185,301 for wid=1 using rgb24 with ratio 75.0% ( 0KB to 0KB), sequence 45, client_options={'rgb_format': 'RGB'}
28,889 client 5 clipboard paste event, data= NETDEV_CHANGE
28,902 process_button_action(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), [b'button-action', 1, 1, 1, [504, 248], [], []])
28,903 do_process_mouse_common(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), 1, [504, 248], -1)
28,903 move_pointer(1, [504, 248], -1) screen_no=-1, device=XTestPointerDevice, position=(504, 248)
28,903 xtest_fake_motion(-1, 504, 248)
28,903 xtest_fake_button(1, 1)
28,904 motion_signaled(WindowModel(0x600022), <X11:MotionNotify {'send_event': '0', 'serial': '0x10a1c', 'delivered_to': '0x600022', 'window': '0x600022', 'root': '0x299', 'subwindow': '0x60002d', 'time': '203569588', 'x': '174', 'y': '48', 'x_root': '504', 'y_root': '248', 'state': '0', 'is_hint': '1', 'same_screen': '1'}>) last mouse user=9431c9d0-db66-842c-d9ff-adda9a89b378
28,926 compress: 0.1ms for 24x13 pixels at 173,41 for wid=1 using rgb24 with ratio 16.1% ( 1KB to 0KB), sequence 46, client_options={'rgb_format': 'RGB', 'lz4': 1, 'flush': 2}
28,926 compress: 0.3ms for 24x13 pixels at 149,41 for wid=1 using rgb24 with ratio 14.3% ( 1KB to 0KB), sequence 47, client_options={'rgb_format': 'RGB', 'lz4': 1, 'flush': 1}
28,927 compress: 0.1ms for 6x13 pixels at 185,301 for wid=1 using rgb24 with ratio 75.0% ( 0KB to 0KB), sequence 48, client_options={'rgb_format': 'RGB'}
28,965 client 5 clipboard paste event, data= NETDEV_CHANGE
28,965 client 5 clipboard paste event, data= NETDEV_CHANGE
28,965 client 5 clipboard pending= false buffer= NETDEV_CHANGE
28,991 process_button_action(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), [b'button-action', 1, 1, 0, [504, 248], [], []])
28,992 do_process_mouse_common(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), 1, [504, 248], -1)
28,992 move_pointer(1, [504, 248], -1) screen_no=-1, device=XTestPointerDevice, position=(504, 248)
28,992 xtest_fake_motion(-1, 504, 248)
28,992 xtest_fake_button(1, 0)
28,992 do_xpra_xfixes_selection_notify_event(<X11:XFSelectionNotify {'send_event': '0', 'serial': '0x10a33', 'delivered_to': '0x40000d', 'window': '0x40000d', 'subtype': '0', 'owner': '0x60002d', 'selection': 'PRIMARY', 'timestamp': '203569677', 'selection_timestamp': '203569677'}>)
28,993 do_selection_notify_event(<X11:XFSelectionNotify {'send_event': '0', 'serial': '0x10a33', 'delivered_to': '0x40000d', 'window': '0x40000d', 'subtype': '0', 'owner': '0x60002d', 'selection': 'PRIMARY', 'timestamp': '203569677', 'selection_timestamp': '203569677'}>) owned=False, was False (owner=0x60002d, xid=0x40000d), enabled=True, can-send=True
28,993 do_owner_changed()
28,993 get_contents(TARGETS, <function ClipboardProxy.schedule_emit_token.<locals>.got_targets at 0x7fdf2d470b00>) owned=False, have-token=False
28,993 requesting local XConvertSelection from child of 'antoine@desktop-eth0:~/projects/Xpra/trunk/src' as 'TARGETS' into 'PRIMARY-TARGETS'
28,993 do_xpra_property_notify_event(<X11:PropertyNotify {'send_event': '0', 'serial': '0x10a40', 'delivered_to': '0x40000d', 'window': '0x40000d', 'atom': 'PRIMARY-TARGETS', 'time': '203569678'}>)
28,993 do_property_notify(<X11:PropertyNotify {'send_event': '0', 'serial': '0x10a40', 'delivered_to': '0x40000d', 'window': '0x40000d', 'atom': 'PRIMARY-TARGETS', 'time': '203569678'}>)
28,993 PRIMARY-TARGETS=b'\xe7\x00\x00\x00\x00\x00\x00\x00\xa5\x01\x00\x .. x00\x00\x00\x00\xa3\x01\x00\x00\x00\x00\x00\x00' (ATOM : 32)
28,994 filter_data(TARGETS, ATOM, 32, ..)
28,994 got_local_contents: calling <function ClipboardProxy.schedule_emit_token.<locals>.got_targets at 0x7fdf2d470b00>('ATOM', 32, b'\xe7\x00\x00\x00\x00\x00\x00\x00\xa5\x01\x00\x .. x00\x00\x00\x00\xa3\x01\x00\x00\x00\x00\x00\x00')
28,994 got_targets: ('UTF8_STRING', 'TEXT', 'COMPOUND_TEXT', 'STRING', 'LENGTH', 'LIST_LENGTH', 'TIMESTAMP', 'HOSTNAME', 'IP_ADDRESS', 'USER', 'CLASS', 'NAME', 'CLIENT_WINDOW', 'OWNER_OS')
28,994 get_contents(UTF8_STRING, <function ClipboardProxy.schedule_emit_token.<locals>.with_targets.<locals>.got_text_target at 0x7fdf2d470560>) owned=False, have-token=False
28,994 requesting local XConvertSelection from child of 'antoine@desktop-eth0:~/projects/Xpra/trunk/src' as 'UTF8_STRING' into 'PRIMARY-UTF8_STRING'
28,994 do_xpra_property_notify_event(<X11:PropertyNotify {'send_event': '0', 'serial': '0x10a43', 'delivered_to': '0x40000d', 'window': '0x40000d', 'atom': 'PRIMARY-TARGETS', 'time': '203569678'}>)
28,994 do_property_notify(<X11:PropertyNotify {'send_event': '0', 'serial': '0x10a43', 'delivered_to': '0x40000d', 'window': '0x40000d', 'atom': 'PRIMARY-TARGETS', 'time': '203569678'}>)
28,994 do_property_notify() property 'PRIMARY-TARGETS' is gone?
Traceback (most recent call last):
File "/usr/lib64/python3.7/site-packages/xpra/x11/gtk_x11/clipboard.py", line 631, in do_property_notify
dtype, dformat = X11Window.GetWindowPropertyType(self.xid, event.atom, True)
File "xpra/x11/bindings/window_bindings.pyx", line 1202, in xpra.x11.bindings.window_bindings.X11WindowBindingsInstance.GetWindowPropertyType
raise BadPropertyType("None type")
xpra.x11.bindings.window_bindings.BadPropertyType: None type
28,995 do_xpra_property_notify_event(<X11:PropertyNotify {'send_event': '0', 'serial': '0x10a5d', 'delivered_to': '0x40000d', 'window': '0x40000d', 'atom': 'PRIMARY-UTF8_STRING', 'time': '203569679'}>)
28,995 do_property_notify(<X11:PropertyNotify {'send_event': '0', 'serial': '0x10a5d', 'delivered_to': '0x40000d', 'window': '0x40000d', 'atom': 'PRIMARY-UTF8_STRING', 'time': '203569679'}>)
28,995 PRIMARY-UTF8_STRING=b'ADDRCONF' (UTF8_STRING : 8)
28,995 filter_data(UTF8_STRING, UTF8_STRING, 8, ..)
28,995 got_local_contents: calling <function ClipboardProxy.schedule_emit_token.<locals>.with_targets.<locals>.got_text_target at 0x7fdf2d470560>('UTF8_STRING', 8, b'ADDRCONF')
28,995 got_text_target(UTF8_STRING, 8, b'ADDRCONF')
28,995 _send_clipboard_token_handler(X11ClipboardProxy(PRIMARY), (('UTF8_STRING', 'TEXT', 'STRING'), ('UTF8_STRING', 'UTF8_STRING', 8, b'ADDRCONF')))
28,995 _munge_raw_selection_to_wire('UTF8_STRING', 'UTF8_STRING', 8, 'ADDRCONF')
28,995 _do_munge_raw_selection_to_wire(UTF8_STRING, UTF8_STRING, 8, <class 'bytes'>:8)
28,995 send_clipboard_token_handler PRIMARY to PRIMARY
28,995 do_xpra_property_notify_event(<X11:PropertyNotify {'send_event': '0', 'serial': '0x10a63', 'delivered_to': '0x40000d', 'window': '0x40000d', 'atom': 'PRIMARY-UTF8_STRING', 'time': '203569680'}>)
28,996 do_property_notify(<X11:PropertyNotify {'send_event': '0', 'serial': '0x10a63', 'delivered_to': '0x40000d', 'window': '0x40000d', 'atom': 'PRIMARY-UTF8_STRING', 'time': '203569680'}>)
28,996 do_property_notify() property 'PRIMARY-UTF8_STRING' is gone?
Traceback (most recent call last):
File "/usr/lib64/python3.7/site-packages/xpra/x11/gtk_x11/clipboard.py", line 631, in do_property_notify
dtype, dformat = X11Window.GetWindowPropertyType(self.xid, event.atom, True)
File "xpra/x11/bindings/window_bindings.pyx", line 1202, in xpra.x11.bindings.window_bindings.X11WindowBindingsInstance.GetWindowPropertyType
raise BadPropertyType("None type")
xpra.x11.bindings.window_bindings.BadPropertyType: None type
29,015 compress: 0.1ms for 6x13 pixels at 185,301 for wid=1 using rgb24 with ratio 75.0% ( 0KB to 0KB), sequence 49, client_options={'rgb_format': 'RGB'}
29,026 client 5 clipboard clipboard token received
29,026 client 5 clipboard targets= UTF8_STRING,TEXT,STRING
29,027 client 5 clipboard target= UTF8_STRING is valid: true
29,027 client 5 clipboard dtype= UTF8_STRING dformat= 8 wire-encoding= bytes
Summarized as:
ADDRCONF
and send it to the client as UTF8_STRING
pending
flagMiddle click:
34,856 process_button_action(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), [b'button-action', 1, 2, 1, [504, 248], [], []])
34,856 do_process_mouse_common(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), 1, [504, 248], -1)
34,857 move_pointer(1, [504, 248], -1) screen_no=-1, device=XTestPointerDevice, position=(504, 248)
34,857 xtest_fake_motion(-1, 504, 248)
34,857 xtest_fake_button(2, 1)
35,028 client 5 clipboard pending= true buffer= ADDRCONF
35,029 client 5 clipboard click event, with pending clipboard datatype= utf8_string , buffer= ADDRCONF
35,029 client 5 clipboard copy event, clipboard buffer= ADDRCONF
35,055 process_button_action(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), [b'button-action', 1, 2, 0, [504, 248], [], []])
35,055 do_process_mouse_common(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), 1, [504, 248], -1)
35,055 move_pointer(1, [504, 248], -1) screen_no=-1, device=XTestPointerDevice, position=(504, 248)
35,056 xtest_fake_motion(-1, 504, 248)
35,056 xtest_fake_button(2, 0)
35,072 compress: 0.1ms for 102x13 pixels at 185,301 for wid=1 using rgb24 with ratio 13.6% ( 5KB to 0KB), sequence 50, client_options={'rgb_format': 'RGB', 'lz4': 1}
36,782 _process_pointer_position(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), [b'pointer-position', 1, [505, 248], [], []]) readonly=False, ui_driver=9431c9d0-db66-842c-d9ff-adda9a89b378
36,783 do_process_mouse_common(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), 1, [505, 248], -1)
36,783 move_pointer(1, [505, 248], -1) screen_no=-1, device=XTestPointerDevice, position=(505, 248)
36,784 xtest_fake_motion(-1, 505, 248)
36,785 motion_signaled(WindowModel(0x600022), <X11:MotionNotify {'send_event': '0', 'serial': '0x10b11', 'delivered_to': '0x600022', 'window': '0x600022', 'root': '0x299', 'subwindow': '0x60002d', 'time': '203577469', 'x': '175', 'y': '48', 'x_root': '505', 'y_root': '248', 'state': '0', 'is_hint': '1', 'same_screen': '1'}>) last mouse user=9431c9d0-db66-842c-d9ff-adda9a89b378
36,786 _process_pointer_position(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), [b'pointer-position', 0, [505, 248], [], []]) readonly=False, ui_driver=9431c9d0-db66-842c-d9ff-adda9a89b378
36,786 do_process_mouse_common(WebSocket(ws socket: 192.168.0.10:10000 <- 192.168.0.108:59511), 0, [505, 248], -1)
36,787 move_pointer(0, [505, 248], -1) screen_no=-1, device=XTestPointerDevice, position=(505, 248)
36,787 xtest_fake_motion(-1, 505, 248)
36,788 motion_signaled(WindowModel(0x600022), <X11:MotionNotify {'send_event': '0', 'serial': '0x10b17', 'delivered_to': '0x600022', 'window': '0x600022', 'root': '0x299', 'subwindow': '0x60002d', 'time': '203577472', 'x': '175', 'y': '48', 'x_root': '505', 'y_root': '248', 'state': '0', 'is_hint': '1', 'same_screen': '1'}>) last mouse user=9431c9d0-db66-842c-d9ff-adda9a89b378
Summary:
Nothing unusual, strange!
Same as Xpra-org/xpra#2896 but for the HTML5 client.
Makes sense to also deal with #11 at the same time.
Issue migrated from trac ticket # 2993
component: html5 | priority: critical
I regularly use file uploads with my wireshark docker image which is using xpra (https://github.com/ffeldhaus/docker-wireshark). With the current stable xpra version 4.0.6-28284 on Ubuntu 20.04, I can upload files normally. With the latest xpra beta 4.1-28292 I get this error when uploading files via the HTML5 client:
2021-01-04 22:15:27,670 client 1 file: 8m , type: , size: 8388608 2021-01-04 22:15:31,447 Error: invalid data size for file '8m' 2021-01-04 22:15:31,448 received 12581964 bytes, expected 8388608 bytes
The xpra config files and setup are the same, but I use Ubuntu 20.04.1 LTS for running xpra stable and Ubuntu 20.10 to run xpra beta.
split from Xpra-org/xpra#1424
Code added in r15242.
Still TODO:
Issue migrated from trac ticket # 842
component: html5 | priority: major | resolution: fixed
The HTML5 client should support text data exchange between the remote and local clipboards.
But! The local clipboard cannot be accessed from any browser at will. You can only access it during a clipboard event, i.e. if the user has pasted something in the browser window.
Therefore, the user would have to copy from their local application, paste into the html5 client, and then use the paste in the remote application. Maybe we can press CTRL+C for them to automate the remote paste?
Anyway, to get data that has been copied into the remote clipboard, we must display some kind of dialog to allow the user to manually copy to their local clipboard: user copies to clipboard in remote application, html5 client prompts with the text, user selects text and copies into their local clipboard.
Issue migrated from trac ticket # 2060
component: html5 | priority: critical | resolution: fixed
Here's a log sample recorded for a 1520x920 window downscaled to 1012x612 for h264, then refreshed using webp.
05,262 damage(0, 0, 1520, 920, {}) wid=2 05,263 do_damage(0, 0, 1520, 920, {}) wid=2, scheduling batching expiry for sequence 317 in 21 ms 05,293 compress: 7.1ms for 1520x920 pixels at 0,0 for wid=2 using h264 with ratio 0.0% ( 5462KB to 1KB), sequence 187, client_options={u'type': u'P', u'frame': 5, u'pts': 25493, 'csc': u'YUV420P', 'scaled_size': (1012, 612)} 05,298 client draw may_paint_now() paint pending= 0 , paint queue length= 1 05,298 client draw do_paint( 1767 bytes of h264 data 1520 x 920 at 0 , 0 ) focused= true 05,305 client draw broadway picture decoded: 2555904 bytes, size 1024 x 624, paint location: 0,0 with infos= undefined 05,308 client draw request_redraw for Window(2) 05,309 client draw decode time for h264 sequence 187 : 10 , flush= 0 05,314 client draw animation frame: 1 windows to paint 05,425 damage(0, 0, 1520, 920, {}) wid=2 05,426 do_damage(0, 0, 1520, 920, {}) wid=2, scheduling batching expiry for sequence 319 in 21 ms 10,017 damage(0, 0, 1520, 920, {}) wid=2 10,018 do_damage(0, 0, 1520, 920, {}) wid=2, scheduling batching expiry for sequence 321 in 21 ms 10,056 compress: 12.4ms for 1520x566 pixels at 0,27 for wid=2 using webp with ratio 1.6% ( 3360KB to 55KB), sequence 189, client_options={'flush': 1, u'quality': 100, u'rgb_format': 'BGRX'} 10,058 compress: 1.1ms for 1520x26 pixels at 0,809 for wid=2 using webp with ratio 6.1% ( 154KB to 9KB), sequence 190, client_options={u'quality': 100, u'rgb_format': 'BGRX'} 10,062 client draw may_paint_now() paint pending= 0 , paint queue length= 1 10,062 client draw do_paint( 56596 bytes of webp data 1520 x 566 at 0 , 27 ) focused= true 10,064 client draw may_paint_now() paint pending= 87296 , paint queue length= 1 10,071 client draw decode time for webp sequence 188 : 8 , flush= 1 10,071 client draw may_paint_now() paint pending= 0 , paint queue length= 1 10,072 client draw do_paint( 9590 bytes of webp data 1520 x 26 at 0 , 809 ) focused= true 10,076 client draw request_redraw for Window(2) 10,077 client draw decode time for webp sequence 189 : 12 , flush= 0 10,077 client draw may_paint_now() paint pending= 0 , paint queue length= 0 10,078 client draw animation frame: 1 windows to paint 10,090 damage(0, 0, 1520, 920, {}) wid=2 10,090 do_damage(0, 0, 1520, 920, {}) wid=2, scheduling batching expiry for sequence 323 in 21 ms 10,128 compress: 11.9ms for 1520x566 pixels at 0,27 for wid=2 using webp with ratio 1.6% ( 3360KB to 55KB), sequence 191, client_options={'flush': 1, u'quality': 100, u'rgb_format': 'BGRX'} 10,129 compress: 1.2ms for 1520x26 pixels at 0,809 for wid=2 using webp with ratio 6.1% ( 154KB to 9KB), sequence 192, client_options={u'quality': 100, u'rgb_format': 'BGRX'} 10,134 client draw may_paint_now() paint pending= 0 , paint queue length= 1 10,134 client draw do_paint( 56596 bytes of webp data 1520 x 566 at 0 , 27 ) focused= true 10,136 client draw may_paint_now() paint pending= 87367 , paint queue length= 1 10,136 client draw decode time for webp sequence 190 : 2 , flush= 1 10,136 client draw may_paint_now() paint pending= 0 , paint queue length= 1 10,136 client draw do_paint( 9710 bytes of webp data 1520 x 26 at 0 , 809 ) focused= true 10,138 client draw request_redraw for Window(2) 10,138 client draw decode time for webp sequence 191 : 3 , flush= 0 10,139 client draw may_paint_now() paint pending= 0 , paint queue length= 0 10,141 client draw animation frame: 1 windows to paint
The broadway decoder reports
client draw broadway picture decoded: 2555904 bytes, size 1024 x 624, paint location: 0,0 with infos= undefined
despite the fact that the encoder reported different scaled dimensions:client_options={u'type': u'P', u'frame': 5, u'pts': 25493, 'csc': u'YUV420P', 'scaled_size': (1012, 612)
.Looks like the image we get from broadway should be cropped before being upscaled.
Issue migrated from trac ticket # 2269
component: html5 | priority: major | resolution: worksforme
I've been working on improving the HTML5 client for our own needs, namely:
- minimally invasive draggable menu (to replace top bar)
- window selection menu
- start menu
- small ui changes (dark background, white window headers)
It's functional but rough around the edges. Not sure if you're interested in taking it on? I can tidy it up a bit more if you are.
There's a lot of file changes here so I'd recommend copying from head at:
[https://github.com/mjharkin/Xpra/tree/dev]
The official page: [http://wiki.webmproject.org/vp8-implementations] is missing some newer options, ie: ogv.js JavaScript media player using Ogg / Vorbis / Theora / Opus / WebM libs compiled with Emscripten
Issue migrated from trac ticket # 2686
component: html5 | priority: minor | keywords: modal windows, on top, no workspace
Hi, I am using xpra to access a remote application using the html5 client, xpra on the server run in seamless mode ( start --start-cmd=/usr/bin/xterm ), If I run a pyqt modal application launcher, two things happen, the pyqt application has z-index 15000, and whatever window I start from this launcher goes below and I cannot use it. The other wrong behaviour is this pyqt launcher is not listed in the upper menu, so If i minimize it than I lose it, and I am not able to show it again..
If I attach the remote session via the xpra client it works correctly, the issue is only with the html5 client.
If I start xpra in destkop mode, it works correctly even with html5 client.
os: ubuntu 18.04
xpra version: 3.0.7-25627-1
020-03-30 12:22:02,516I have enclosed a picture
Kindly regards
Marco
Issue migrated from trac ticket # 2452
component: html5 | priority: major | keywords: clipboard
Prepping to test Xpra-org/xpra#2312, I started realizing that the clipboard sync even for text was extraordinarily crazy-making. (It does suddenly occur to me that this might be a result of enabling the
chrome://flags/#enable-experimental-web-platform-features
as indicated in Xpra-org/xpra#2312#comment:6 of that ticket - I'll check once I finish this ticket.)Using Chrome 77 on Windows 7 against a 3.0-24048 Fedora 30 server.
It took some time to isolate the behavior, but I finally came up with a reproducible set of steps that are as not-crazy-making as possible.
I launched the session with:
xpra start :13 --no-daemon --bind-tcp=0.0.0.0:1234 --bind-ws=0.0.0.0:1237 --start-child=xterm --start-child=xterm --exit-with-children
I then used one of the xterms to launch Firefox, then used a bing translate tab for a copy/paste input/output field, and word locally (I was hoping to be pasting images... a text file ought to work).
- Copy the text 'test1' locally, paste into bing - pastes as expected, with the following output in the server logs.
2019-10-17 10:27:04,950 client is requesting an unknown target: 'text/plain;charset=utf-8' 2019-10-17 10:27:04,951 valid targets: UTF8_STRING, text/plain 2019-10-17 10:27:04,951 dropping the request
- Now type 'test2' into bing field and copy, paste back to local editor - fails, instead pasing 'test1'.
- Now type 'test3' locally and copy, paste back into bing - fails, pasting 'test2' (which was last copied in the session) instead, and again outputting the request drop message in server logs.
- Now, without any new copying, paste back into the local editor - at this point, it will also paste 'test2' (the local clipboard has now been updated with the contents from the session clipboard, when the paste event took place?).
- Now go back to the session and type/copy 'test4', then paste back to the local editor - and again it pastes 'test2', so the copy event server side does not seem to be updating the clipboard locally...?
- Now, just to see if you've been made crazy yet, type/copy 'test5' locally and paste into bing - it fails and instead pastes... 'test4', which was last sync'd to the server clipboard when the type/copy event happened, if I'm not totally lost yet... ohh, and now you see that dropping request message in the server logs again.
- And now, once again with no new copy event... just paste whatever is hiding in the local clipboard into the local editor... and, now we see 'test4', which it looks like got sync'd back to the local clipboard not on the copy event, or on the paste event locally... but only when a paste event server-side is detected?
Really, that was as "clear" as I could make it... I think.
Hi I am new to Xpra and I am trying to use local html client to test my requirement,
When I use xpra start --bind-tcp=0.0.0.0:10000 --start=xterm --key-shortcut='Alt+F10':toggle_fullscreen
to launch the application in fullscreen it wont work. Can someone help me whats the wrong I am doing in command line or is there something else I am missing. Attaching log file for reference.
:2.log
See Xpra-org/xpra#2793 comment:9 and previous comments.
Issue migrated from trac ticket # 2410
component: html5 | priority: minor
Hi,
I wanted to ask if there are plans to support HiDPI (e.g. Retina) screens for HTML 5 clients. Out of the box the HTML 5 client will use the css width / height properties to render the server screen, which will result in relatively low resolution displays (the virtualized screen resolution is small).
With some small changes we managed to get around this by using the window.devicePixelRatio to render a higher res screen on the server and scale it back via css transform to the original screen (plus some small changes on the mouse handling). After this the screens look nice and sharp on Retina displays as well.
Would such a patch be considered for inclusion in the repository? Many screens these days tend to have HIDPI resolutions, so some kind of better support might be welcomed by the community.
Many thanks for your great work on this project,
Regards,
Andras
Improve #2 and add:
Same as Xpra-org/xpra#1817 but for 3.0:
Rather than shipping a copy, we should add a dependency and create a symlink, the same way we handle jquery.
Here's what lint shows:
W: xpra-html5: duplicate-font-file usr/share/xpra/www/icons/materialicons-regular.ttf also in fonts-material-design-icons-iconfont
Issue migrated from trac ticket # 3005
component: html5 | priority: major
Hi,
The problem is that it's impossible to write any accented character (á, é, etc) using the HTML5 client. Using the desktop client works fine.
I'm using Chrome on Windows to connect to an Ubuntu server using the last beta version xpra v4.1-r28309, but the problem also reproduces using the last stable version and using Firefox. I'm using a Spanish keyboard (as reference, this is the layout: https://commons.wikimedia.org/wiki/File:KB_Spanish.svg).
The procedure to write for example á is to press [[']] and then [a]. The first key is the key to the right to [ñ] in the keyboard.
At the beggining the HTML5 client doesn't send the accent key code and writes an apostrophe, so looking at other issues I added CHARCODE_TO_NAME[222] = "dead_acute" in Keycodes.js.
Then it recognizes the ['] key, but it doesn't write the á character. To write it, I have to press
[']
[any other key] [a]. Pressing ['] [a] doesn't generate any output.This is the output when pressing ['] [a] (no character is written).
2021-01-18 10:23:38,051 client 1 keyboard last keycode pressed= 0 , keycode= 222 , pressed= true , str= Dead 2021-01-18 10:23:38,052 client 1 keyboard processKeyEvent( true , [object KeyboardEvent] ) key= Quote keycode= 222 2021-01-18 10:23:38,052 client 1 keyboard _get_keyboard_layout() keyboard_layout= es 2021-01-18 10:23:38,053 will try levels: [0, 4, 1, 5, 2, 6, 3, 7] 2021-01-18 10:23:38,053 do_get_keycode(222, 'dead_acute', True, [], 222, 'dead', 0)=48 (level=0, shift=False, mode=0, keysyms=['dead_acute', 'dead_diaeresis', 'braceleft', 'braceleft']) 2021-01-18 10:23:38,053 process_key_action([b'key-action', 1, b'dead_acute', True, (), 222, b'dead', 222, 0]) server keycode=48, group=0 2021-01-18 10:23:38,054 set_keyboard_layout_group(0) ignored, no layout groups support 2021-01-18 10:23:38,054 set_keyboard_layout_group(0) ignored, value unchanged 2021-01-18 10:23:38,055 filtered_modifiers_set([])=set() 2021-01-18 10:23:38,055 filtered_modifiers_set([])=set() 2021-01-18 10:23:38,055 is_modifier(48) not found 2021-01-18 10:23:38,056 handle_key((1, True, 'dead_acute', 222, 48, [], False, True)) 2021-01-18 10:23:38,056 handle keycode pressing 48: key 'dead_acute' 2021-01-18 10:23:38,056 fake_key(48, True) 2021-01-18 10:23:38,080 client 1 keyboard last keycode pressed= 222 , keycode= 222 , pressed= false , str= Dead 2021-01-18 10:23:38,080 client 1 keyboard processKeyEvent( false , [object KeyboardEvent] ) key= Quote keycode= 222 2021-01-18 10:23:38,081 process_key_action([b'key-action', 1, b'dead_acute', False, (), 222, b'dead', 222, 0]) server keycode=48, group=0 2021-01-18 10:23:38,082 set_keyboard_layout_group(0) ignored, no layout groups support 2021-01-18 10:23:38,082 set_keyboard_layout_group(0) ignored, value unchanged 2021-01-18 10:23:38,083 filtered_modifiers_set([])=set() 2021-01-18 10:23:38,083 filtered_modifiers_set([])=set() 2021-01-18 10:23:38,084 is_modifier(48) not found 2021-01-18 10:23:38,084 handle_key((1, False, 'dead_acute', 222, 48, [], False, True)) 2021-01-18 10:23:38,084 handle keycode unpressing 48: key 'dead_acute' 2021-01-18 10:23:38,084 fake_key(48, False) 2021-01-18 10:23:39,890 client 1 keyboard last keycode pressed= 0 , keycode= 65 , pressed= true , str= ?? 2021-01-18 10:23:39,890 client 1 keyboard processKeyEvent( true , [object KeyboardEvent] ) key= KeyA keycode= 65 2021-01-18 10:23:39,891 client 1 keyboard _get_keyboard_layout() keyboard_layout= es 2021-01-18 10:23:39,892 will try levels: [0, 4, 1, 5, 2, 6, 3, 7] 2021-01-18 10:23:39,892 do_get_keycode(65, 'aacute', True, [], 65, '?', 0)=-1, 0 (keyname translation) 2021-01-18 10:23:39,892 process_key_action([b'key-action', 1, b'aacute', True, (), 65, b'\xc3\xa1', 65, 0]) server keycode=-1, group=0 2021-01-18 10:23:39,893 client 1 keyboard last keycode pressed= 65 , keycode= 65 , pressed= false , str= a 2021-01-18 10:23:39,893 filtered_modifiers_set([])=set() 2021-01-18 10:23:39,894 client 1 keyboard processKeyEvent( false , [object KeyboardEvent] ) key= KeyA keycode= 65 2021-01-18 10:23:39,894 filtered_modifiers_set([])=set() 2021-01-18 10:23:39,895 process_key_action([b'key-action', 1, b'a', False, (), 65, b'a', 65, 0]) server keycode=-1, group=0
This is the output when I type ['][e][a] (á is written)
2021-01-18 10:26:00,471 client 1 keyboard last keycode pressed= 0 , keycode= 222 , pressed= true , str= Dead 2021-01-18 10:26:00,471 client 1 keyboard processKeyEvent( true , [object KeyboardEvent] ) key= Quote keycode= 222 2021-01-18 10:26:00,472 client 1 keyboard _get_keyboard_layout() keyboard_layout= es 2021-01-18 10:26:00,481 will try levels: [0, 4, 1, 5, 2, 6, 3, 7] 2021-01-18 10:26:00,482 do_get_keycode(222, 'dead_acute', True, [], 222, 'dead', 0)=48 (level=0, shift=False, mode=0, keysyms=['dead_acute', 'dead_diaeresis', 'braceleft', 'braceleft']) 2021-01-18 10:26:00,482 process_key_action([b'key-action', 1, b'dead_acute', True, (), 222, b'dead', 222, 0]) server keycode=48, group=0 2021-01-18 10:26:00,482 set_keyboard_layout_group(0) ignored, no layout groups support 2021-01-18 10:26:00,482 set_keyboard_layout_group(0) ignored, value unchanged 2021-01-18 10:26:00,483 filtered_modifiers_set([])=set() 2021-01-18 10:26:00,483 filtered_modifiers_set([])=set() 2021-01-18 10:26:00,484 is_modifier(48) not found 2021-01-18 10:26:00,484 handle_key((1, True, 'dead_acute', 222, 48, [], False, True)) 2021-01-18 10:26:00,484 handle keycode pressing 48: key 'dead_acute' 2021-01-18 10:26:00,484 fake_key(48, True) 2021-01-18 10:26:00,541 client 1 keyboard last keycode pressed= 222 , keycode= 222 , pressed= false , str= Dead 2021-01-18 10:26:00,541 client 1 keyboard processKeyEvent( false , [object KeyboardEvent] ) key= Quote keycode= 222 2021-01-18 10:26:00,543 process_key_action([b'key-action', 1, b'dead_acute', False, (), 222, b'dead', 222, 0]) server keycode=48, group=0 2021-01-18 10:26:00,543 set_keyboard_layout_group(0) ignored, no layout groups support 2021-01-18 10:26:00,543 set_keyboard_layout_group(0) ignored, value unchanged 2021-01-18 10:26:00,544 filtered_modifiers_set([])=set() 2021-01-18 10:26:00,544 filtered_modifiers_set([])=set() 2021-01-18 10:26:00,545 is_modifier(48) not found 2021-01-18 10:26:00,545 handle_key((1, False, 'dead_acute', 222, 48, [], False, True)) 2021-01-18 10:26:00,545 handle keycode unpressing 48: key 'dead_acute' 2021-01-18 10:26:00,545 fake_key(48, False) 2021-01-18 10:26:02,319 client 1 keyboard last keycode pressed= 0 , keycode= 69 , pressed= true , str= ?? 2021-01-18 10:26:02,320 client 1 keyboard processKeyEvent( true , [object KeyboardEvent] ) key= KeyE keycode= 69 2021-01-18 10:26:02,320 client 1 keyboard _get_keyboard_layout() keyboard_layout= es 2021-01-18 10:26:02,321 will try levels: [0, 4, 1, 5, 2, 6, 3, 7] 2021-01-18 10:26:02,321 do_get_keycode(69, 'eacute', True, [], 69, '?', 0)=-1, 0 (keyname translation) 2021-01-18 10:26:02,321 process_key_action([b'key-action', 1, b'eacute', True, (), 69, b'\xc3\xa9', 69, 0]) server keycode=-1, group=0 2021-01-18 10:26:02,322 filtered_modifiers_set([])=set() 2021-01-18 10:26:02,322 filtered_modifiers_set([])=set() 2021-01-18 10:26:02,384 client 1 keyboard last keycode pressed= 69 , keycode= 69 , pressed= false , str= e 2021-01-18 10:26:02,384 client 1 keyboard processKeyEvent( false , [object KeyboardEvent] ) key= KeyE keycode= 69 2021-01-18 10:26:02,386 process_key_action([b'key-action', 1, b'e', False, (), 69, b'e', 69, 0]) server keycode=-1, group=0 2021-01-18 10:26:02,386 filtered_modifiers_set([])=set() 2021-01-18 10:26:02,387 filtered_modifiers_set([])=set() 2021-01-18 10:26:04,033 client 1 keyboard last keycode pressed= 0 , keycode= 65 , pressed= true , str= a 2021-01-18 10:26:04,035 client 1 keyboard processKeyEvent( true , [object KeyboardEvent] ) key= KeyA keycode= 65 2021-01-18 10:26:04,035 client 1 keyboard _get_keyboard_layout() keyboard_layout= es 2021-01-18 10:26:04,036 client 1 keyboard last keycode pressed= 65 , keycode= 65 , pressed= false , str= a 2021-01-18 10:26:04,036 client 1 keyboard processKeyEvent( false , [object KeyboardEvent] ) key= KeyA keycode= 65 2021-01-18 10:26:04,036 will try levels: [0, 4, 1, 5, 2, 6, 3, 7] 2021-01-18 10:26:04,037 do_get_keycode(65, 'a', True, [], 65, 'a', 0)=38 (level=0, shift=False, mode=0, keysyms=['a', 'A', 'ae', 'AE']) 2021-01-18 10:26:04,037 process_key_action([b'key-action', 1, b'a', True, (), 65, b'a', 65, 0]) server keycode=38, group=0 2021-01-18 10:26:04,037 set_keyboard_layout_group(0) ignored, no layout groups support 2021-01-18 10:26:04,037 set_keyboard_layout_group(0) ignored, value unchanged 2021-01-18 10:26:04,038 filtered_modifiers_set([])=set() 2021-01-18 10:26:04,038 filtered_modifiers_set([])=set() 2021-01-18 10:26:04,039 is_modifier(38) not found 2021-01-18 10:26:04,039 handle_key((1, True, 'a', 65, 38, [], False, True)) 2021-01-18 10:26:04,039 handle keycode pressing 38: key 'a' 2021-01-18 10:26:04,039 fake_key(38, True) 2021-01-18 10:26:04,040 process_key_action([b'key-action', 1, b'a', False, (), 65, b'a', 65, 0]) server keycode=38, group=0 2021-01-18 10:26:04,040 set_keyboard_layout_group(0) ignored, no layout groups support 2021-01-18 10:26:04,041 set_keyboard_layout_group(0) ignored, value unchanged 2021-01-18 10:26:04,041 filtered_modifiers_set([])=set() 2021-01-18 10:26:04,042 filtered_modifiers_set([])=set() 2021-01-18 10:26:04,042 is_modifier(38) not found 2021-01-18 10:26:04,042 handle_key((1, False, 'a', 65, 38, [], False, True)) 2021-01-18 10:26:04,043 handle keycode unpressing 38: key 'a' 2021-01-18 10:26:04,043 fake_key(38, False)
This is the output using the desktop client (works fine, writes á):
2021-01-18 10:41:56,326 client 1 @30.809 mask_to_names(<flags 0 of type Gdk.ModifierType>) GetKeyState(VK_NUMLOCK)=0, names=[] 2021-01-18 10:41:56,346 client 1 @30.811 parse_key_event(<Gdk.EventKey object at 0x000000005b3d0680 (void at 0x0000000047eb20b0)>, True)=<GTKKeyEvent object, contents: {'modifiers': [], 'keyname': 'dead_acute', 'keyval': 65105, 'keycode': 222, 'group': 0, 'string': '', 'pressed': True}> 2021-01-18 10:41:56,347 client 1 @30.811 handle_key_action(ClientWindow(1), <GTKKeyEvent object, contents: {'modifiers': [], 'keyname': 'dead_acute', 'keyval': 65105, 'keycode': 222, 'group': 0, 'string': '', 'pressed': True}>) wid=1 2021-01-18 10:41:56,347 client 1 @30.813 key_handled_as_shortcut(ClientWindow(1), 'dead_acute', [], True) shortcuts=None 2021-01-18 10:41:56,348 client 1 @30.814 send_delayed_key() delayed_event=None 2021-01-18 10:41:56,348 client 1 @30.814 send_key_action(1, <GTKKeyEvent object, contents: {'modifiers': [], 'keyname': 'dead_acute', 'keyval': 65105, 'keycode': 222, 'group': 0, 'string': '', 'pressed': True}>) 2021-01-18 10:41:56,349 will try levels: [0, 4, 1, 5, 2, 6, 3, 7] 2021-01-18 10:41:56,349 do_get_keycode(222, 'dead_acute', True, [], 65105, '', 0)=48 (level=0, shift=False, mode=0, keysyms=['dead_acute', 'dead_diaeresis', 'braceleft', 'braceleft']) 2021-01-18 10:41:56,350 process_key_action(['key-action', 1, b'dead_acute', True, (), 65105, b'', 222, 0]) server keycode=48, group=0 2021-01-18 10:41:56,350 set_keyboard_layout_group(0) ignored, value unchanged 2021-01-18 10:41:56,351 filtered_modifiers_set([])=set() 2021-01-18 10:41:56,351 filtered_modifiers_set([])=set() 2021-01-18 10:41:56,351 is_modifier(48) not found 2021-01-18 10:41:56,352 handle_key((1, True, 'dead_acute', 65105, 48, [], False, True)) 2021-01-18 10:41:56,352 handle keycode pressing 48: key 'dead_acute' 2021-01-18 10:41:56,352 fake_key(48, True) 2021-01-18 10:41:56,353 scheduling key repeat timer with delay 500 for dead_acute / 48 2021-01-18 10:41:56,389 client 1 @30.872 mask_to_names(<flags 0 of type Gdk.ModifierType>) GetKeyState(VK_NUMLOCK)=0, names=[] 2021-01-18 10:41:56,390 client 1 @30.873 parse_key_event(<Gdk.EventKey object at 0x000000005b3d0680 (void at 0x0000000047a9df20)>, False)=<GTKKeyEvent object, contents: {'modifiers': [], 'keyname': 'dead_acute', 'keyval': 65105, 'keycode': 222, 'group': 0, 'string': '', 'pressed': False}> 2021-01-18 10:41:56,395 client 1 @30.874 handle_key_action(ClientWindow(1), <GTKKeyEvent object, contents: {'modifiers': [], 'keyname': 'dead_acute', 'keyval': 65105, 'keycode': 222, 'group': 0, 'string': '', 'pressed': False}>) wid=1 2021-01-18 10:41:56,395 client 1 @30.875 key_handled_as_shortcut(ClientWindow(1), 'dead_acute', [], False) shortcuts=None 2021-01-18 10:41:56,396 client 1 @30.876 send_delayed_key() delayed_event=None 2021-01-18 10:41:56,396 client 1 @30.876 send_key_action(1, <GTKKeyEvent object, contents: {'modifiers': [], 'keyname': 'dead_acute', 'keyval': 65105, 'keycode': 222, 'group': 0, 'string': '', 'pressed': False}>) 2021-01-18 10:41:56,397 process_key_action(['key-action', 1, b'dead_acute', False, (), 65105, b'', 222, 0]) server keycode=48, group=0 2021-01-18 10:41:56,397 set_keyboard_layout_group(0) ignored, value unchanged 2021-01-18 10:41:56,397 filtered_modifiers_set([])=set() 2021-01-18 10:41:56,398 filtered_modifiers_set([])=set() 2021-01-18 10:41:56,398 is_modifier(48) not found 2021-01-18 10:41:56,398 handle_key((1, False, 'dead_acute', 65105, 48, [], False, True)) 2021-01-18 10:41:56,399 handle keycode unpressing 48: key 'dead_acute' 2021-01-18 10:41:56,399 fake_key(48, False) 2021-01-18 10:41:56,762 client 1 @31.102 mask_to_names(<flags 0 of type Gdk.ModifierType>) GetKeyState(VK_NUMLOCK)=0, names=[] 2021-01-18 10:41:56,764 filtered_modifiers_set([])=set() 2021-01-18 10:41:56,765 filtered_modifiers_set([])=set() 2021-01-18 10:41:57,047 client 1 @31.533 mask_to_names(<flags 0 of type Gdk.ModifierType>) GetKeyState(VK_NUMLOCK)=0, names=[] 2021-01-18 10:41:57,048 client 1 @31.533 parse_key_event(<Gdk.EventKey object at 0x000000005b3d07c0 (void at 0x0000000047a9ddc0)>, True)=<GTKKeyEvent object, contents: {'modifiers': [], 'keyname': 'a', 'keyval': 97, 'keycode': 65, 'group': 0, 'string': 'a', 'pressed': True}> 2021-01-18 10:41:57,075 client 1 @31.533 handle_key_action(ClientWindow(1), <GTKKeyEvent object, contents: {'modifiers': [], 'keyname': 'a', 'keyval': 97, 'keycode': 65, 'group': 0, 'string': 'a', 'pressed': True}>) wid=1 2021-01-18 10:41:57,075 client 1 @31.534 key_handled_as_shortcut(ClientWindow(1), 'a', [], True) shortcuts=None 2021-01-18 10:41:57,076 client 1 @31.534 send_delayed_key() delayed_event=None 2021-01-18 10:41:57,076 client 1 @31.534 send_key_action(1, <GTKKeyEvent object, contents: {'modifiers': [], 'keyname': 'a', 'keyval': 97, 'keycode': 65, 'group': 0, 'string': 'a', 'pressed': True}>) 2021-01-18 10:41:57,077 will try levels: [0, 4, 1, 5, 2, 6, 3, 7] 2021-01-18 10:41:57,077 do_get_keycode(65, 'a', True, [], 97, 'a', 0)=38 (level=0, shift=False, mode=0, keysyms=['a', 'A', 'ae', 'AE']) 2021-01-18 10:41:57,077 process_key_action(['key-action', 1, b'a', True, (), 97, b'a', 65, 0]) server keycode=38, group=0 2021-01-18 10:41:57,077 set_keyboard_layout_group(0) ignored, value unchanged 2021-01-18 10:41:57,078 filtered_modifiers_set([])=set() 2021-01-18 10:41:57,078 filtered_modifiers_set([])=set() 2021-01-18 10:41:57,079 is_modifier(38) not found 2021-01-18 10:41:57,079 handle_key((1, True, 'a', 97, 38, [], False, True)) 2021-01-18 10:41:57,079 handle keycode pressing 38: key 'a' 2021-01-18 10:41:57,079 fake_key(38, True) 2021-01-18 10:41:57,080 scheduling key repeat timer with delay 500 for a / 38
The bug is also present with --no-keyboard-sync. I have attached also setxkbmap info for the server.
If there is anything else I can provide, please let me know.
Regards.
The code is old and ugly.
We should take advantage of modern browser technologies to cleanup the code.
Related to Xpra-org/xpra#1788. See also r18987, Xpra-org/xpra#1670, Xpra-org/xpra#1492.
Links:
Issue migrated from trac ticket # 2154
component: html5 | priority: blocker | resolution: needinfo | keywords: keyboard
I know that there is a long guide how to report keyboard layout mapping problems, but I think here the issue is clearly in the HTML5 JS code.
Most of the users to whom I tried to provide remote access through a browser report that input is not working even with the en_US layout. It is only possible to input numbers into xterm. Other keys cause beeps and either spaces or numbers are typed instead of, e.g., letters.
For me, en_US layout is working at the beginning. Switching to Russian layout breaks everything and switching back to en_US does not help. Here are logs from the JS console (Browser version: Firefox 65.0 (64-bit). OS: Ubuntu 18.04, LANG=en_US.UTF-8. Xpra 2.4.2 is running inside a CentOS 7 Docker container).
debug enabled for: Array [] 1:438:5 connection_progress( Initializing , , 20 ) 1:399:6 connection_progress( Connecting to server , localhost:8888/display/1/ , 40 ) 1:399:6 we have webworker support Client.js:320:3 we can use websocket in webworker Client.js:329:5 connection_progress( Opening WebSocket connection , ws://localhost:8888/display/1/ , 60 ) Client.js:228:2 connection_progress( WebSocket connection established , , 80 ) Client.js:228:2 sending hello Client.js:942:3 return all encodings: Array(6) [ "jpeg", "png", "rgb", "rgb32", "h264", "mpeg1" ] Client.js:865:3 return all encodings: Array(6) [ "jpeg", "png", "rgb", "rgb32", "h264", "mpeg1" ] Client.js:865:3 getFirstBrowserLanguage()= en-US Utilities.js:135:3 getKeyboardLayout()= us Utilities.js:150:3 hello capabilities: [object Object] Client.js:956:2 got hello: server version 2.4.2 accepted our connection Client.js:228:2 server screen sizes: Array(1571) [ (2) […], (2) […], (2) […], (2) […], (2) […], (2) […], (2) […], (2) […], (2) […], (2) […], … ] Client.js:1648:5 connection_progress( Session started , , 100 ) Client.js:228:2 startup complete Client.js:228:2 connection-established Client.js:228:2 server connection is OK Client.js:890:4
Now, if I type something into
xterm
having en_US layout active, everything works fine. If I try to switch the layout to Russian, I get the following in the JS consoleinput language changed from null to ru Client.js:595:3
I don't see symbols in
xterm
, only spaces, but I think this is fonts-related issue.Then, if I switch back to en_US layout and try to type something, I see nothing in the JS console about input language change. And typing causes beeps.
This would allow us to more closely match the python client and copy more data types.
chrome ticket: Issue 897289: clipboard raw data access permission: ..to handle types beyond text and images, with read and write of arbitrary types. Scenarios include interop with native apps and the operating system, as well as between web applications
Related tickets: Xpra-org/xpra#2312, Xpra-org/xpra#812, Xpra-org/xpra#1844
Issue migrated from trac ticket # 2909
component: html5 | priority: major
Version: xpra v4.1-r27688
After I connect through Xpra proxy, I get the the screenshot attached. It is not possible to scroll to the bottom of the screen and the desktop seems to be shifted on the top.
Do you have an idea where the problem could be?
Issue migrated from trac ticket # 2292
component: html5 | priority: minor | resolution: fixed
The html5 client override the client clipboard on the first click in the client window after connection.
How to reproduce:
- Connect to xpra server with the html5 client
- Copy string in xpra remote, for example "xpratest", and paste it on your computer. It's works as expected.
- Copy string, for example "mylocalstring" from your computer and paste it in the remote client. It's work as expected.
- Quit the html5 client (reload the page or even close the tab)
- Reconnect with the html5 client and interact with it.
- The local clipboard (the one on the computer) and remote (xpra server) clipboard will now be set to "xpratest". It's happen with a click, not even a text selection or ctrl-c.
Xpra client: html5 tags/2.5 (r22658) and also trunk r22658 on ArchLinux? and Chromium 74
Xpra Server: 2.5.1-22431 on Debian 9
Xpra config for clipboard:
desktop-fullscreen (used) = True clipboard = 'yes' clipboard-direction = 'both' clipboard-filter-file = '' local-clipboard = 'CLIPBOARD' remote-clipboard = 'CLIPBOARD'
Fullscreen desktop with openbox.
The clipboard debug log of the problem is attached.
Follow up from #173: jquery can cause us problems and is an extra layer sitting in between our code and the browser.
As You Don't Need jQuery! puts it: Free yourself from the chains of jQuery by embracing and understanding the modern Web API and discovering various directed libraries to help you fill in the gaps.
Lots of good advice and examples for moving away from jquery there.
Issue migrated from trac ticket # 1147
component: html5 | priority: major | resolution: fixed
As reported here: [https://xpra.org/list/2016-March/001492.html],
the keyboard layout detection code [/browser/xpra/tags/v0.16.x/src/html5/include/xpra_client.js#L424] works with IE but not chrome or Firefox.
The main difficulty is to ensure this is installed on all the build environment as there aren't many packages for it...
Issue migrated from trac ticket # 1839
component: html5 | priority: major | resolution: fixed
Split from #25, the error that comes up is
RangeError: Source is too large
.
Splitting this from #74 (comment:15)
Reproducible with Firefox on any platform.
This sounds like Capturing a Paste Event in Firefox: The paste event has been supported in major browsers for some time now, but interestingly Firefox doesn’t trigger the event unless the user’s cursor is currently focussed in an editable region.
Unfortunately, the Firefox bug is meant to have been fixed already and sprinkling contenteditable=true
in every div doesn't make any difference. Neither does listening for clipboard events on all contenteditable
elements as suggested here: [https://stackoverflow.com/a/19269040/428751].
More answers here: JavaScript get clipboard data on paste event (Cross browser)
Issue migrated from trac ticket # 2312
component: html5 | priority: major | resolution: fixed
We want to transfer the pixel data as
image/png
and set it as best we can usingsetData
or newer methods (#1844).See THE DEFINITIVE GUIDE TO COPYING AND PASTING IN JAVASCRIPT
The difficulty here is that because the html5 clibpoard is greedy, we need to choose png as soon as we get the clipboard event so we can send the binary data with the token.
Some pointers in Xpra-org/xpra#812#comment:29
Follow up from Xpra-org/xpra#1789, this is the html5 version.
Follow up from Xpra-org/xpra#890:
Hopefully we can find at least one browser / OS combination that works?
Or figure out the problem with broadway? (RangeError: Source is too large
)
Original tickets: Xpra-org/xpra#1341, Xpra-org/xpra#1424
Issue migrated from trac ticket # 1338
component: html5 | priority: major | keywords: WebRTC AES html
Xpra html mode works over HTTP so it uses plain text URL. It means that a password and AES key can easily be intercepted. But we can use WebRTC transport with or without signaling server.
There is now a javascript version we can use: https://github.com/PolkaJS/rencode (ISC License)
See createImageBitmap(): It allows you to decode an image in the background, and get access to a new ImageBitmap primitive, which you can draw into a canvas in the same way you would an element, another canvas, or a video.
Issue migrated from trac ticket # 2574
component: html5 | priority: major | resolution: fixed
The first problem, solved for "spacebar" in r25130, is that we don't get the keyname we expect so we have to map the character to its (X11) keyname.
The second problem is that the keyname may map to a keycode that requires modifiers to be accessed.
ie: "&" shows up as "7"
Issue migrated from trac ticket # 1775
component: html5 | priority: minor
xpra v2.3-r18646
If viewing a video over html5 with sound forwarding, sometimes there are delays of a few seconds in the sound transfer. I've tested with firefox and chromium and several audio codecs, though not all combinations.
After the delay the sound goes on where it stopped. This leads to a mismatch of video and sound, especially annoying with mismatching dialogues of film characteres. Side effect: after terminating the video player, the sound goes on until the buffer is empty.
I assume the sound is buffered somewhere and not synchronized with xpra display transfer. Maybe an option to enforce video-sound synchronization that drops parts of sound if needed would make sense.
For myself it is not that important as I don't need that, just want to report the observation.
Issue migrated from trac ticket # 1484
component: html5 | priority: major | resolution: fixed
Follow up from Xpra-org/xpra#1487:
Hello,
Somebody already told about this function but seems not declared ticket (at least I have not found, correct me if I am wrong).
So it would perfect if that function appears in the following versions.
Issue migrated from trac ticket # 845
component: html5 | priority: critical | resolution: fixed
We should be able to process sound-data packets to allow sound forwarding to the HTML5 client.
Web Audio API's decodeAudioData doesn't seem to decode an Xpra mp3 frame, at least in Chrome 42.
Right now I am experimenting with aurora.js which is able to decode wav, flac, mp3 among others in javascript.
However, the packets have to be processed in the main page, essentially in the same thread as drawing. I expect this will have a significant impact on performance...
Following up #69.
Many new chrome features can be found here: https://chromestatus.com/features
Worth a look:
xpra://
urls. (and xpra+ssl
, etc as per Xpra-org/xpra#1894)navigator.deviceMemory
to the server? (and avoid using video on low power devices)A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.