Skip to content

Commit 24320e3

Browse files
committed
Make new messages on thread etc
1 parent ef62741 commit 24320e3

4 files changed

Lines changed: 54 additions & 22 deletions

File tree

src/chat/chatLogic.js

Lines changed: 27 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,7 @@ export class ChatChannel {
4040
as a replacement for an existing one.
4141
The old one iis left, and the two are linked
4242
*/
43-
async updateMessage (text, oldMsg = null, deleteIt) {
43+
async updateMessage (text, oldMsg = null, deleteIt, thread = null) {
4444
const sts = []
4545
const now = new Date()
4646
const timestamp = '' + now.getTime()
@@ -68,8 +68,14 @@ export class ChatChannel {
6868
if (me) {
6969
sts.push($rdf.st(message, ns.foaf('maker'), me, chatDocument))
7070
}
71+
if (thread) {
72+
sts.push($rdf.st(thread, ns.sioc('has_member'), message, chatDocument))
73+
if (!thread.doc().sameTerm(message.doc())) {
74+
sts.push($rdf.st(thread, ns.sioc('has_member'), message, thread.doc()))
75+
}
76+
}
7177
try {
72-
await store.updater.update([], sts)
78+
await store.updater.updateMany([], sts)
7379
} catch (err) {
7480
const msg = 'Error saving chat message: ' + err
7581
debug.warn(msg)
@@ -86,8 +92,27 @@ export class ChatChannel {
8692
async deleteMessage (message) {
8793
return this.updateMessage('(message deleted)', message, true)
8894
}
95+
96+
// Create a new thread of replies to the thread root message
97+
// or returns one which already exists
98+
99+
async createThread (threadRoot) {
100+
const already = store.each(threadRoot, ns.sioc('has_reply'), null, threadRoot.doc())
101+
.filter(thread => store.holds(thread, ns.rdf('type'), ns.sioc('Thread'), thread.doc()))
102+
if (already.length > 0) return already[0]
103+
104+
const thread = $rdf.sym(threadRoot.uri + '-thread')
105+
const insert = [
106+
$rdf.st(thread, ns.rdf('type'), ns.sioc('Thread'), thread.doc()),
107+
$rdf.st(threadRoot, ns.sioc('has_reply'), thread, thread.doc()),
108+
];
109+
await store.updater.update([], insert)
110+
return thread
111+
}
89112
} // class ChatChannel
90113

114+
//////////// Utility functons
115+
91116
export async function allVersions (message) {
92117
let versions = [ message ]
93118
let m = message

src/chat/infinite.js

Lines changed: 8 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -114,16 +114,7 @@ export async function infiniteMessageArea (dom, wasStore, chatChannel, options)
114114
}
115115
}
116116

117-
const messages = store
118-
.statementsMatching(
119-
chatChannel,
120-
ns.wf('message'),
121-
null,
122-
messageTable.chatDocument
123-
)
124-
.map(st => {
125-
return st.object
126-
})
117+
const messages = store.each(chatChannel, ns.wf('message'), null, messageTable.chatDocument)
127118
const stored = {}
128119
for (const m of messages) {
129120
stored[m.uri] = true
@@ -404,9 +395,9 @@ export async function infiniteMessageArea (dom, wasStore, chatChannel, options)
404395
/// ///// Infinite scroll
405396
//
406397
// @@ listen for swipe past end event not just button
407-
if (options.infinite) {
408-
const scrollBackbuttonTR = dom.createElement('tr')
409-
const scrollBackbuttonCell = scrollBackbuttonTR.appendChild(
398+
if (true) { // ws options.infinite but need for non-infinite
399+
const titleTR = dom.createElement('tr')
400+
const scrollBackbuttonCell = titleTR.appendChild(
410401
dom.createElement('td')
411402
)
412403
// up traingles: noun_1369237.svg
@@ -426,13 +417,13 @@ export async function infiniteMessageArea (dom, wasStore, chatChannel, options)
426417
scrollBackbuttonCell.appendChild(scrollBackbutton)
427418
setScrollBackbuttonIcon()
428419
*/
429-
const dateCell = scrollBackbuttonTR.appendChild(dom.createElement('td'))
420+
const dateCell = titleTR.appendChild(dom.createElement('td'))
430421
dateCell.style =
431422
'text-align: center; vertical-align: middle; color: #888; font-style: italic;'
432423
dateCell.textContent = widgets.shortDate(date.toISOString(), true) // no time, only date
433424

434425
// @@@@@@@@@@@ todo move this button to other end of message cell, o
435-
const scrollForwardButtonCell = scrollBackbuttonTR.appendChild(
426+
const scrollForwardButtonCell = titleTR.appendChild(
436427
dom.createElement('td')
437428
)
438429
if (options.includeRemoveButton) {
@@ -463,9 +454,9 @@ export async function infiniteMessageArea (dom, wasStore, chatChannel, options)
463454

464455
if (!newestFirst) {
465456
// opposite end from the entry field
466-
messageTable.insertBefore(scrollBackbuttonTR, messageTable.firstChild) // If not newestFirst
457+
messageTable.insertBefore(titleTR, messageTable.firstChild) // If not newestFirst
467458
} else {
468-
messageTable.appendChild(scrollBackbuttonTR) // newestFirst
459+
messageTable.appendChild(titleTR) // newestFirst
469460
}
470461
}
471462

src/chat/message.js

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -237,7 +237,7 @@ export async function renderMessageRow (channelObject, message, fresh, options,
237237
return
238238
}
239239
const toolsTR = dom.createElement('tr')
240-
const tools = messageToolbar(message, messageRow, userContext, channelObject)
240+
const tools = messageToolbar(message, messageRow, { ...userContext, chatOptions: options }, channelObject)
241241
tools.style =
242242
'border: 0.05em solid #888; border-radius: 0 0 0.7em 0.7em; border-top: 0; height:3.5em; background-color: #fff;' // @@ fix
243243
if (messageRow.nextSibling) {
@@ -325,7 +325,7 @@ export function renderMessageEditor (channelObject, messageTable, userContext, o
325325

326326
let message
327327
try {
328-
message = await channelObject.updateMessage(text, originalMessage)
328+
message = await channelObject.updateMessage(text, originalMessage, null, options.thread)
329329
} catch (err) {
330330
const statusArea = userContext.statusArea || messageEditor
331331
statusArea.appendChild(

src/chat/messageTools.js

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -120,7 +120,16 @@ export function messageToolbar (message, messageRow, userContext, channelObject)
120120
}
121121
}
122122

123-
// alain TODO allow chat owner to fully delete message + sentiments and replacing messages
123+
async function replyInThread () {
124+
const thread = await channelObject.createThread(message)
125+
const options = userContext.chatOptions
126+
if (!options) throw new Error('replyInThread: missing options')
127+
options.showThread(thread, options)
128+
closeToolbar() // a one-off action
129+
}
130+
131+
132+
// alain: TODO allow chat owner to fully delete message + sentiments and replacing messages
124133

125134
const div = dom.createElement('div')
126135
// is message deleted ?
@@ -258,6 +267,13 @@ export function messageToolbar (message, messageRow, userContext, channelObject)
258267
)
259268
)
260269
}
270+
// Reply buttton
271+
272+
if (store.any(message, ns.dct('created'))) { // Looks like a messsage? Bar can be used for other things
273+
div.appendChild(widgets.button(dom, icons.iconBase + REPLY_ICON, 'Reply in thread', async () => {
274+
await replyInThread()
275+
}))
276+
}
261277
// X button to remove the tool UI itself
262278
const cancelButton = div.appendChild(widgets.cancelButton(dom))
263279
cancelButton.style.float = 'right'

0 commit comments

Comments
 (0)