}
},
handle_blist_message: function(method, params) {
- bid = params.proto + ":" + params.account + ":" + params.buddy;
- // Create buddy entry in blist if none exists yet
- if (window.blist[bid] === undefined) {
- window.blist[bid] = {
- proto: params.proto,
- account: params.account,
- buddy: params.buddy,
- status: {}
- };
- }
- if (method == "buddy_status_changed") {
- window.blist[bid].status = params.status;
- } else if (method == "buddy_icon_changed") {
- var url = "/icons/" + window.session_id + "/" + params.url;
- console.log(url);
- window.blist[bid].bicon_url = url;
- }
- window.reactor.refs.buddy_list.onChange(window.blist);
+ window.reactor.refs.buddy_list.handleBlistMessage(method, params);
},
handle_conversations_message: function(method, params) {
console.log("conversations:", method, params);
- bid = params.proto + ":" + params.account + ":" + params.buddy;
- if (window.conversations[bid] === undefined) {
- window.conversations[bid] = {
- proto: params.proto,
- account: params.account,
- buddy: params.buddy,
- messages: [],
- visible: false,
- type_state: "stopped"
- };
- }
-
if (method == "recv_im") {
window.reactor.refs.conversations.handleRecvIm(params);
- } else if (method == "buddy_typing_state") {
- window.conversations[bid].type_state = params.state;
}
- // TODO: repaint conversations window
},
handle_session_message: function(method, params) {
console.log("session:", method, params);
var BuddyListItem = React.createClass({
propTypes: {
+ proto: React.PropTypes.string.isRequired,
+ account: React.PropTypes.string.isRequired,
+ buddy: React.PropTypes.string.isRequired,
+ status: React.PropTypes.object.isRequired,
bicon_url: React.PropTypes.string,
- display_name: React.PropTypes.string.isRequired,
- status_msg: React.PropTypes.string
},
render: function () {
- return <div className="buddy">
+ // This is kinda janky, but it works...
+ var openWindowFunc = window.reactor.refs.conversations.switchToConv.bind(
+ window.reactor.refs.conversations,
+ this.props.proto, this.props.account, this.props.buddy
+ );
+ return <div className="buddy" onClick={openWindowFunc}>
<img className="buddyicon" src={this.props.bicon_url} />
<div className="buddycontainer">
- <div className="buddyname buddytext">{this.props.display_name}</div>
- <div className="buddytext">{this.props.status_msg}</div>
+ <div className="buddyname buddytext">{this.props.buddy}</div>
+ <div className="buddytext">{this.props.status.status_msg}</div>
</div>
</div>;
}
var BuddyList = React.createClass({
// buddy state is a dictionary buid -> {proto, account, buddy, status, bicon_url}
getInitialState: function () {
- return {"buddies": [] };
+ return {"buddies": {} };
},
- // TODO: move handleBlistMessage to this class from dispatcher
- onChange: function(newData) {
- // parse out newData and convert to structure expected by widget
- var buddy_ids = Object.keys(newData);
- buddy_ids.sort();
- var buddies = [];
- for (var i = 0 ; i < buddy_ids.length ; i++) {
- var buddy = newData[buddy_ids[i]];
- buddies.push({
- bicon_url: buddy.bicon_url,
- display_name: buddy.buddy,
- status_msg: buddy.status.status_msg
- });
+ handleBlistMessage: function(method, params) {
+ var bid = params.proto + ":" + params.account + ":" + params.buddy;
+ if (this.state.buddies[bid] === undefined) {
+ this.state.buddies[bid] = {
+ proto: params.proto,
+ account: params.account,
+ buddy: params.buddy,
+ status: {}
+ };
}
- this.setState( { "buddies": buddies } );
+ if (method == "buddy_status_changed") {
+ this.state.buddies[bid].status = params.status;
+ } else if (method == "buddy_icon_changed") {
+ var url = "/icons/" + window.session_id + "/" + params.url;
+ console.log(url);
+ this.state.buddies[bid].bicon_url = url;
+ }
+ this.forceUpdate();
},
render: function () {
- // for each thing in this.state:
- // render thing
- var things = [];
- for (var i = 0 ; i < this.state.buddies.length ; i++) {
- var s = this.state.buddies[i];
- things.push(BuddyListItem(this.state.buddies[i]));
- }
- return <div className="buddy_list">{ things }</div>;
+ var keys = Object.keys(this.state.buddies);
+ keys.sort();
+ var buddies = keys.map(function(key) { return BuddyListItem(this.state.buddies[key]); }, this);
+ return <div className="buddy_list">{ buddies }</div>;
}
});
conversations: []
};
},
+ switchToConv: function(proto, account, buddy) {
+ var bid = proto + ":" + account + ":" + buddy;
+ var active_convs = this.state.conversations.filter(function(obj) { return obj.visible; });
+ for (var i = 0 ; i < active_convs.length; i++) {
+ if (active_convs[i].buddy.id == bid) {
+ this.handleTabSwitch(i);
+ return;
+ }
+ }
+ // Not found; append it to conversations
+ this.getConversation(proto, account, buddy);
+ this.state.focused_tab = active_convs.length;
+ this.forceUpdate();
+ },
handleTabSwitch: function(focusedTabIndex) {
console.log("Switching to tab " + focusedTabIndex);
this.setState({ focused_tab: focusedTabIndex,
// 1) Dispatch IM to buddy
var active_convs = this.state.conversations.filter(function(obj) { return obj.visible; });
var conv = active_convs[this.state.focused_tab];
- var contact = window.blist[conv.buddy.id];
+ var contact = window.reactor.refs.buddy_list.state.buddies[conv.buddy.id];
var params = {
proto: contact.proto,
account: contact.account,