2023-12-27 17:25:49 +00:00
window . matrix = ( opts ) => new Proxy ( {
2023-12-27 21:31:42 +00:00
el : null , // HTML element
2023-12-27 17:25:49 +00:00
plugin : {
type : 'network' ,
2024-01-03 14:23:34 +00:00
name : '[Matrix]' ,
2023-12-27 21:31:42 +00:00
description : 'a standardized decentralized privacy-friendly protocol' ,
2023-12-27 17:25:49 +00:00
url : 'https://matrix.org' ,
2023-12-27 21:31:42 +00:00
protocol : 'matrix://' ,
2023-12-27 17:25:49 +00:00
video : false ,
audio : false ,
chat : true ,
scene : true
} ,
2024-01-09 11:05:13 +00:00
channel : '#xrfragment-test:matrix.org' ,
server : 'https://matrix.org' ,
username : '' ,
auth : 'via password' ,
authkey : '' ,
client : null ,
roomid : '' ,
2023-12-27 17:25:49 +00:00
html : {
2023-12-27 21:31:42 +00:00
generic : ( opts ) => ` <div>
2024-01-09 11:05:13 +00:00
< div target = "_blank" class = "badge ruler" > matrix < a onclick = "frontend.plugin.matrix.info()" > < i class = "gg-info right" > < / i > < / a > < / d i v >
< table id = "matrix" >
2023-12-27 21:31:42 +00:00
< tr >
< td > channel < / t d >
< td >
2024-01-09 11:05:13 +00:00
< input type = "text" id = "channel" placeholder = "#xrfragment:matrix.org" value = "${opts.plugin.channel}" / >
2023-12-27 21:31:42 +00:00
< / t d >
< / t r >
< tr >
< td > server < / t d >
2024-01-09 11:05:13 +00:00
< td >
< input type = "text" id = "server" placeholder = "https://matrix.org" value = "${opts.plugin.server}" / >
2023-12-27 21:31:42 +00:00
< / t d >
< / t r >
< tr >
< td > user < / t d >
< td >
< input type = "text" id = "username" placeholder = "@you:matrix.org" / >
< / t d >
< / t r >
< tr >
2023-12-28 09:22:54 +00:00
< td > auth < / t d >
2023-12-27 21:31:42 +00:00
< td >
2023-12-28 09:22:54 +00:00
< select id = "auth" >
2023-12-27 21:31:42 +00:00
< option > via password < / o p t i o n >
< option > via access token < / o p t i o n >
< / s e l e c t >
< / t d >
< / t r >
2023-12-27 17:25:49 +00:00
< tr >
2023-12-27 21:31:42 +00:00
< td > < / t d >
2023-12-27 17:25:49 +00:00
< td >
2024-01-09 11:05:13 +00:00
< input type = "password" id = "secret" placeholder = "enter password" / >
2023-12-27 17:25:49 +00:00
< / t d >
< / t r >
< / t a b l e >
2023-12-27 21:31:42 +00:00
< small style = "display:inline-block;float:right" > Support for Oauth / OpenID is < a href = "https://matrix.org/blog/#openid-connect" target = "_blank" > in progress < / a > < / s m a l l >
2024-01-03 14:23:34 +00:00
< br >
2023-12-27 17:25:49 +00:00
< / d i v >
`
} ,
init ( ) {
2024-01-03 14:23:34 +00:00
frontend . plugin [ 'matrix' ] = this
2023-12-27 17:25:49 +00:00
$connections . chatnetwork = $connections . chatnetwork . concat ( [ this ] )
$connections . scene = $connections . scene . concat ( [ this ] )
2023-12-27 21:31:42 +00:00
this . reactToConnectionHrefs ( )
2024-01-09 11:05:13 +00:00
this . nickname = localStorage . getItem ( "nickname" ) || ` human ${ String ( Math . random ( ) ) . substr ( 5 , 4 ) } `
document . addEventListener ( 'network.connect' , ( e ) => this . connect ( e . detail ) )
document . addEventListener ( 'network.init' , ( ) => {
let meeting = network . getMeetingFromUrl ( document . location . href )
if ( meeting . match ( this . plugin . protocol ) ) {
this . parseLink ( meeting )
}
} )
2023-12-27 21:31:42 +00:00
} ,
connect ( opts ) {
console . log ( "connecting " + this . plugin . name )
2024-01-09 11:05:13 +00:00
this . channel = document . querySelector ( "#matrix input#channel" ) . value
this . server = document . querySelector ( "#matrix input#server" ) . value
this . username = document . querySelector ( "#matrix input#username" ) . value
this . auth = document . querySelector ( "#matrix select#auth" ) . value
let secret = document . querySelector ( "#matrix input#secret" ) . value
document . querySelector ( "#matrix input#secret" ) . value = ''
let credentials = { baseUrl : this . server }
if ( this . auth == 'via access token' ) {
credentials . accessToken = secret
credentials . userId = this . username
}
this . client = Matrix . sdk . createClient ( credentials )
if ( this . auth == 'via password' ) {
this . client . login ( "m.login.password" , { "user" : this . username , password : secret } )
. then ( ( ) => this . onMatrixConnect ( ) )
. catch ( ( ) => window . notify ( "authentication was not succesful 😞" ) )
} else this . onMatrixConnect ( )
} ,
onMatrixConnect ( ) {
// token: this.matrixclient.getAccessToken()
this . client . startClient ( )
client . once ( 'sync' , function ( state , prevState , res ) {
if ( state == 'PREPARED' ) this . setupListeners ( )
else console . log ( "state: " + state )
} ) ;
} ,
setupListeners ( ) {
let rooms = this . client . getRooms ( ) ;
rooms . forEach ( room => {
console . log ( room ) ;
} ) ;
this . client . on ( "Room.timeline" , function ( event , room , toStartOfTimeline ) {
if ( event . room _id && event . room _id == this . roomid ) {
console . dir ( event ) ;
}
} ) ;
2023-12-27 17:25:49 +00:00
} ,
config ( opts ) {
opts = { ... opts , ... this . plugin }
2023-12-27 21:31:42 +00:00
this . el = document . createElement ( 'div' )
2023-12-27 17:25:49 +00:00
let html = this . html . generic ( opts )
for ( let i in opts ) {
if ( this . html [ i ] ) html += this . html [ i ] ( opts )
}
2023-12-27 21:31:42 +00:00
this . el . innerHTML = html
2023-12-28 09:22:54 +00:00
this . el . querySelector ( '#auth' ) . addEventListener ( 'change' , ( e ) => {
this . el . querySelector ( '#secret' ) . setAttribute ( 'placeholder' , ` enter ${ e . target . value . replace ( /.* / , '' ) } ` )
} )
2023-12-27 21:31:42 +00:00
return this . el
} ,
2024-01-09 11:05:13 +00:00
info ( opts ) {
window . notify ( ` ${ this . plugin . name } is ${ this . plugin . description } , it is the hottest internet technology available at this moment.<br>Read more about it <a href=" ${ this . plugin . url } " target="_blank">here</a>.<br>You can basically make up a new channelname or use an existing one ` )
} ,
parseLink ( url ) {
if ( ! url . match ( this . plugin . protocol ) ) return
let parts = url . replace ( this . plugin . protocol , '' ) . split ( "/" )
if ( parts [ 0 ] == 'r' ) { // room
let server = parts . split ( "/" ) [ 1 ] . replace ( /:.*/ , '' )
let channel = parts . split ( "/" ) [ 1 ] . replace ( /.*:/ , '' )
$connections . show ( )
$connections . selectedChatnetwork = this . plugin . name
$connections . selectedScene = this . plugin . name
this . el . querySelector ( '#channel' ) . value = ` # ${ channel } : ${ server } `
this . el . querySelector ( '#server' ) . value = server
console . log ( "configured matrix" )
}
return false
} ,
2023-12-27 21:31:42 +00:00
reactToConnectionHrefs ( ) {
xrf . addEventListener ( 'href' , ( opts ) => {
let { mesh } = opts
if ( ! opts . click ) return
2024-01-09 11:05:13 +00:00
this . parseLink ( mesh . userData . href )
let href = mesh . userData . href
let isLocal = href [ 0 ] == '#'
let isTeleport = href . match ( /(pos=|http:)/ )
if ( isLocal && ! isTeleport && this . href . send ) this . href . send ( { href } )
2023-12-27 17:25:49 +00:00
} )
2024-01-09 11:05:13 +00:00
let hashvars = xrf . URI . parse ( document . location . hash )
if ( hashvars . meet ) this . parseLink ( hashvars . meet . string )
2023-12-27 17:25:49 +00:00
}
} ,
{
// auto-trigger events on changes
get ( data , k , receiver ) { return data [ k ] } ,
set ( data , k , v ) {
let from = data [ k ]
data [ k ] = v
2023-12-27 21:31:42 +00:00
//switch( k ){
// default: matrix.opts.scene.dispatchEvent({type:`matrix.${k}.change`, from, to:v})
//}
2023-12-27 17:25:49 +00:00
}
} )
document . addEventListener ( '$connections:ready' , ( e ) => {
matrix ( e . detail ) . init ( )
} )