Merge branch 'bullet' of cwtch.im/ui into master

This commit is contained in:
erinn 2019-02-03 01:29:11 +00:00 committed by Gogs
commit ba9d712f54
9 changed files with 268 additions and 53 deletions

View File

@ -35,6 +35,7 @@ type GrandCentralDispatcher struct {
_ func() `signal:"ClearMessages"` _ func() `signal:"ClearMessages"`
_ func() `signal:"ResetMessagePane"` _ func() `signal:"ResetMessagePane"`
_ func(mID uint) `signal:"Acknowledged"` _ func(mID uint) `signal:"Acknowledged"`
_ func(title string) `signal:"SetToolbarTitle"`
// profile-area stuff // profile-area stuff
_ func(name, onion, image string) `signal:"UpdateMyProfile"` _ func(name, onion, image string) `signal:"UpdateMyProfile"`
@ -115,7 +116,14 @@ func (this *GrandCentralDispatcher) loadMessagesPane(handle string) {
if len(handle) == 32 { // LOAD GROUP if len(handle) == 32 { // LOAD GROUP
log.Debugf("LOADING GROUP %s", handle) log.Debugf("LOADING GROUP %s", handle)
tl := the.Peer.GetGroup(handle).GetTimeline() group := the.Peer.GetGroup(handle)
tl := group.GetTimeline()
nick, _ := group.GetAttribute("nick")
if nick == "" {
this.SetToolbarTitle(handle)
} else {
this.SetToolbarTitle(nick)
}
log.Debugf("messages: %d", len(tl)) log.Debugf("messages: %d", len(tl))
for i := range tl { for i := range tl {
if tl[i].PeerID == the.Peer.GetProfile().Onion { if tl[i].PeerID == the.Peer.GetProfile().Onion {
@ -143,6 +151,14 @@ func (this *GrandCentralDispatcher) loadMessagesPane(handle string) {
return return
} // ELSE LOAD CONTACT } // ELSE LOAD CONTACT
contact, _ := the.Peer.GetProfile().GetContact(handle)
nick,_ := contact.GetAttribute("name")
if nick == "" {
this.SetToolbarTitle(handle)
} else {
this.SetToolbarTitle(nick)
}
messages := this.UIState.GetMessages(handle) messages := this.UIState.GetMessages(handle)
for i := range messages { for i := range messages {
from := messages[i].From from := messages[i].From

View File

@ -1,8 +1,6 @@
package gothings package gothings
import ( import (
"cwtch.im/cwtch/event"
"cwtch.im/cwtch/model"
"cwtch.im/ui/go/constants" "cwtch.im/ui/go/constants"
"cwtch.im/ui/go/gobjects" "cwtch.im/ui/go/gobjects"
"cwtch.im/ui/go/the" "cwtch.im/ui/go/the"
@ -39,20 +37,7 @@ func (this *InterfaceState) AddContact(c *gobjects.Contact) {
if the.Peer.GetContact(c.Handle) == nil { if the.Peer.GetContact(c.Handle) == nil {
decodedPub, _ := base32.StdEncoding.DecodeString(strings.ToUpper(c.Handle)) decodedPub, _ := base32.StdEncoding.DecodeString(strings.ToUpper(c.Handle))
the.Peer.AddContact(c.DisplayName, c.Handle, decodedPub, c.Trusted)
pp := &model.PublicProfile{Name: c.DisplayName, Ed25519PublicKey: decodedPub[:32], Trusted: c.Trusted, Blocked: false, Onion: c.Handle, Attributes: make(map[string]string)}
pp.SetAttribute("name", c.DisplayName)
the.Peer.GetProfile().Contacts[c.Handle] = pp
if c.Trusted {
the.Peer.GetProfile().TrustPeer(c.Handle)
}
the.CwtchApp.EventBus().Publish(event.NewEvent(event.SetPeerAttribute, map[event.Field]string{
event.RemotePeer: c.Handle,
event.Key: "name",
event.Data: c.DisplayName,
}))
go the.Peer.PeerWithOnion(c.Handle) go the.Peer.PeerWithOnion(c.Handle)
} }

View File

@ -165,7 +165,6 @@ func loadCwtchData(gcd *gothings.GrandCentralDispatcher) {
groups := the.Peer.GetGroups() groups := the.Peer.GetGroups()
for i := range groups { for i := range groups {
log.Infof("adding saved group %v", groups[i])
group := the.Peer.GetGroup(groups[i]) group := the.Peer.GetGroup(groups[i])
group.NewMessage = make(chan model.Message) group.NewMessage = make(chan model.Message)
the.Peer.JoinServer(group.GroupServer) the.Peer.JoinServer(group.GroupServer)

View File

@ -18,6 +18,10 @@ Item {
readonly property real ratio: height / width readonly property real ratio: height / width
readonly property string cwtch_background_color: '#EEEEFF'
readonly property string cwtch_color: '#B09CBC'
readonly property string cwtch_dark_color: '#4B3557'
FontAwesome { // PRETTY BUTTON ICONS FontAwesome { // PRETTY BUTTON ICONS
id: awesome id: awesome
resource: "qrc:/qml/fonts/fontawesome.ttf" resource: "qrc:/qml/fonts/fontawesome.ttf"
@ -138,10 +142,13 @@ Item {
readonly property int groupProfilePane: 4 readonly property int groupProfilePane: 4
readonly property int addGroupPane: 5 readonly property int addGroupPane: 5
property string title
Item {} // empty Item {} // empty
OverlayPane { // messagePane OverlayPane { // messagePane
title: theStack.title
anchors.fill: parent anchors.fill: parent
} }
@ -202,5 +209,9 @@ Item {
popup.visible = true popup.visible = true
anmPopup.restart() anmPopup.restart()
} }
onSetToolbarTitle: function(str) {
theStack.title = str
}
} }
} }

View File

@ -2,15 +2,44 @@ import QtGraphicalEffects 1.0
import QtQuick 2.7 import QtQuick 2.7
import QtQuick.Controls 2.4 import QtQuick.Controls 2.4
import QtQuick.Controls.Material 2.0 import QtQuick.Controls.Material 2.0
import QtQuick.Controls 1.4
import QtQuick.Layouts 1.3 import QtQuick.Layouts 1.3
import "../widgets" import "../widgets"
import "../widgets/controls" as Awesome import "../widgets/controls" as Awesome
import "../fonts/Twemoji.js" as T import "../fonts/Twemoji.js" as T
import "../utils.js" as Utils
import "../styles"
ColumnLayout { ColumnLayout {
Layout.fillWidth: true Layout.fillWidth: true
width:parent.width
Text {
Layout.fillWidth: true
text: parent.toolbar.text + " Bulletin Board"
}
TextField {
id: filter
placeholderText: "Search.."
style: CwtchTextFieldStyle{}
anchors.left: parent.left
anchors.right: parent.right
anchors.margins: 10
onTextChanged: {
bulletinView.filter = text
if (bulletinView.model.get(bulletinView.currentIndex).title.indexOf(text) == -1) {
bulletinView.currentIndex = -1
}
}
}
Flickable { // THE MESSAGE LIST ITSELF Flickable { // THE MESSAGE LIST ITSELF
id: sv id: sv
@ -18,10 +47,9 @@ ColumnLayout {
Layout.alignment: Qt.AlignLeft | Qt.AlignTop Layout.alignment: Qt.AlignLeft | Qt.AlignTop
Layout.fillHeight: true Layout.fillHeight: true
Layout.minimumWidth: parent.width Layout.minimumWidth: parent.width
Layout.maximumWidth: parent.width
Layout.fillWidth: true Layout.fillWidth: true
contentWidth: colMessages.width contentWidth: bulletin.width
contentHeight: colMessages.height contentHeight: bulletin.height
boundsBehavior: Flickable.StopAtBounds boundsBehavior: Flickable.StopAtBounds
maximumFlickVelocity: 800 maximumFlickVelocity: 800
@ -30,20 +58,28 @@ ColumnLayout {
target: gcd target: gcd
onClearMessages: function() { onClearMessages: function() {
messagesModel.clear() //jsonModel4.clear()
} }
onAppendMessage: function(handle, from, displayName, message, image, mid, fromMe, ts) { onAppendMessage: function(handle, from, displayName, message, image, mid, fromMe, ts) {
messagesModel.append({ var msg
"_handle": handle, try {
"_from": from, msg = JSON.parse(message)
"_displayName": displayName, } catch (e) {
"_message": parse(message, 12), return
"_image": image, }
"_mid": mid, if (msg.o != 2) return
"_fromMe": fromMe,
"_ts": ts, if (msg.t != undefined) {
jsonModel4.insert(0,{
"title":msg.t,
"body": msg.b,
"selected":false,
"from": from,
"displayName": displayName,
"timestamp": ts
}) })
}
if (sv.contentY + sv.height >= sv.contentHeight - colMessages.height && sv.contentHeight > sv.height) { if (sv.contentY + sv.height >= sv.contentHeight - colMessages.height && sv.contentHeight > sv.height) {
sv.contentY = sv.contentHeight - sv.height sv.contentY = sv.contentHeight - sv.height
@ -51,35 +87,158 @@ ColumnLayout {
} }
} }
ScrollBar.vertical: ScrollBar{ ScrollBar.vertical: ScrollBar{
policy: ScrollBar.AlwaysOn policy: ScrollBar.AlwaysOn
} }
ListView {
id: bulletinView
anchors.left: parent.left
anchors.leftMargin: 10
anchors.topMargin: 10
width: parent.width - 50
height: parent.height - 20
orientation: Qt.Vertical
spacing: 10
model: jsonModel4
property string filter: ""
delegate:
Item {
width: parent.width
height: title.indexOf(bulletinView.filter) >= 0 ? (selected ? texttitle.height + textbody.height + replybtn.height + 8 : texttitle.height * 2) : 0
visible: title.indexOf(bulletinView.filter) >= 0
Column {
width: parent.width
RowLayout {
Button {
text: selected ? "-" : "+"
style: CwtchExpandingButton{}
}
Text {
id: texttitle
text: '<b>' + Utils.htmlEscaped(title) + '</b> by ' + from + "<br/>" + timestamp
leftPadding: 10
topPadding: 5
bottomPadding:5
color: windowItem.cwtch_dark_color
}
MouseArea {
anchors.fill: parent
onClicked: {
selected = !selected
bulletinView.currentIndex = index
}
}
}
Rectangle {
height: 1
color: windowItem.cwtch_color
anchors {
left: parent.left
right: parent.right
}
}
Text {
id: textbody
visible: selected
text: Utils.htmlEscaped(body)
wrapMode: TextEdit.Wrap
leftPadding: 10
topPadding: 10
width: parent.width - 50
}
SimpleButton {
id: replybtn
visible: selected
text: "reply"
anchors.right: parent.right
anchors.rightMargin:10
onClicked: {
console.log("REPLYING!!!")
gcd.broadcast("ResetMessagePane")
theStack.pane = theStack.messagePane
gcd.loadMessagesPane(from)
overlayStack.overlay = overlayStack.chatOverlay
}
}
}
}
focus: true
onCurrentItemChanged: console.log(model.get(bulletinView.currentIndex).title + ' selected')
ListModel {
id: jsonModel4
}
}
}
GroupBox {
title: qsTr("New Bulletin")
Layout.fillWidth: true
RowLayout {
Layout.fillWidth: true
width: parent.width
ColumnLayout { ColumnLayout {
id: colMessages Layout.fillWidth: true
width: sv.width
ListModel { // MESSAGE OBJECTS ARE STORED HERE ... Text {
id: messagesModel text: "Post a new Bulletin Post"
} }
Item { height: 6 } TextField {
id: newposttitle
placeholderText: "Title.."
Layout.fillWidth: true
style: CwtchTextFieldStyle{}
}
Repeater { // ... AND DISPLAYED HERE TextArea {
model: messagesModel id: newpostbody
delegate: Message { Layout.fillWidth: true
handle: _handle style: CwtchTextAreaStyle{}
from: _from }
displayName: _displayName
message: "bulletinbulletinbulletin"
image: _image SimpleButton { // SEND MESSAGE BUTTON
messageID: _mid id: btnSend
fromMe: _fromMe icon: "regular/paper-plane"
timestamp: _ts text: "post"
anchors.right: parent.right
anchors.rightMargin: 2
property int nextMessageID: 1
onClicked: {
if (newposttitle.text != "" && newpostbody.text != "") {
var msg = JSON.stringify({"o":2, "t":newposttitle.text, "b":newpostbody.text})
gcd.sendMessage(msg, nextMessageID++)
}
newposttitle.text = ""
newpostbody.text = ""
} }
} }
} }
} }
}
} }

View File

@ -9,10 +9,12 @@ import "../overlays"
ColumnLayout { ColumnLayout {
Layout.fillWidth: true Layout.fillWidth: true
property alias title: toolbar.text
StackToolbar { StackToolbar {
text: "open privacy exec" id: toolbar
//text: "open privacy exec"
aux.onClicked: { aux.onClicked: {
theStack.pane = gcd.currentOpenConversation.length == 32 ? theStack.groupProfilePane : theStack.userProfilePane theStack.pane = gcd.currentOpenConversation.length == 32 ? theStack.groupProfilePane : theStack.userProfilePane

View File

@ -0,0 +1,21 @@
import QtQuick.Controls.Styles 1.4
import QtQuick 2.7
ButtonStyle {
background: Rectangle {
width:25
height:25
color: windowItem.cwtch_dark_color
border.color: windowItem.cwtch_color
}
label: Text {
renderType: Text.NativeRendering
verticalAlignment: Text.AlignVCenter
horizontalAlignment: Text.AlignHCenter
font.family: "Monospace"
font.pointSize: 8
color: windowItem.cwtch_background_color
text: control.text
}
}

View File

@ -0,0 +1,8 @@
import QtQuick.Controls.Styles 1.4
import QtQuick 2.7
TextAreaStyle {
textColor: "black"
backgroundColor: windowItem.cwtch_background_color
}

View File

@ -0,0 +1,14 @@
import QtQuick.Controls.Styles 1.4
import QtQuick 2.7
TextFieldStyle {
textColor: "black"
background: Rectangle {
radius: 2
implicitWidth: 100
implicitHeight: 24
color: windowItem.cwtch_background_color
border.color: windowItem.cwtch_color
}
}