Fixed forwarding bug + add group management button

This commit is contained in:
Justin Ferrari 2023-01-13 16:38:39 -05:00
parent 2ffe55caa0
commit 2cbe969d9d
6 changed files with 383 additions and 207 deletions

View File

@ -93,46 +93,46 @@
"selectfile": "Select file", "selectfile": "Select file",
"dragfile": "Drag and drop backup here" "dragfile": "Drag and drop backup here"
}, },
"settings":{ "settings": {
"generalinfo":"General Account Info", "generalinfo": "General Account Info",
"address":"Address", "address": "Address",
"publickey":"Public Key", "publickey": "Public Key",
"settings":"Settings", "settings": "Settings",
"account":"Account", "account": "Account",
"security":"Security", "security": "Security",
"qr_login_menu_item":"QR Login", "qr_login_menu_item": "QR Login",
"qr_login_description_1":"Scan this code to unlock your wallet on other device using the same password which you logged in with.", "qr_login_description_1": "Scan this code to unlock your wallet on other device using the same password which you logged in with.",
"qr_login_description_2":"Choose a password which you will use to unlock your wallet on other device after scanning the QR code.", "qr_login_description_2": "Choose a password which you will use to unlock your wallet on other device after scanning the QR code.",
"qr_login_button_1":"Show login QR code", "qr_login_button_1": "Show login QR code",
"qr_login_button_2":"Generate login QR code", "qr_login_button_2": "Generate login QR code",
"notifications":"Notifications", "notifications": "Notifications",
"accountsecurity":"Account Security", "accountsecurity": "Account Security",
"password":"Password", "password": "Password",
"download":"Download Backup File", "download": "Download Backup File",
"choose":"Please choose a password to encrypt your backup with. (This can be the same as the one you logged in with, or different)", "choose": "Please choose a password to encrypt your backup with. (This can be the same as the one you logged in with, or different)",
"block":"Block Notifications (Coming Soon...)", "block": "Block Notifications (Coming Soon...)",
"playsound":"Play Sound", "playsound": "Play Sound",
"shownotifications":"Show Notifications", "shownotifications": "Show Notifications",
"nodeurl":"Node Url", "nodeurl": "Node Url",
"nodehint":"Select a node from the default list of nodes above or add a custom node to the list above by clicking on the button below", "nodehint": "Select a node from the default list of nodes above or add a custom node to the list above by clicking on the button below",
"addcustomnode":"Add Custom Node", "addcustomnode": "Add Custom Node",
"addandsave":"Add And Save", "addandsave": "Add And Save",
"protocol":"Protocol", "protocol": "Protocol",
"domain":"Domain", "domain": "Domain",
"port":"Port", "port": "Port",
"import":"Import Nodes", "import": "Import Nodes",
"export":"Export Nodes", "export": "Export Nodes",
"deletecustomnode":"Remove All Custom Nodes", "deletecustomnode": "Remove All Custom Nodes",
"warning":"Your existing nodes will be deleted and from backup new created.", "warning": "Your existing nodes will be deleted and from backup new created.",
"snack1":"Successfully deleted and added standard nodes", "snack1": "Successfully deleted and added standard nodes",
"snack2":"UI conected to node", "snack2": "UI conected to node",
"snack3":"Successfully added and saved custom node", "snack3": "Successfully added and saved custom node",
"snack4":"Nodes successfully saved as", "snack4": "Nodes successfully saved as",
"snack5":"Nodes successfully imported", "snack5": "Nodes successfully imported",
"exp1":"Export Private Master Key", "exp1": "Export Private Master Key",
"exp2":"Export Master Key", "exp2": "Export Master Key",
"exp3":"Export", "exp3": "Export",
"exp4":"Please choose a wallet to backup the private master key." "exp4": "Please choose a wallet to backup the private master key."
}, },
"appinfo": { "appinfo": {
"blockheight": "Block Height", "blockheight": "Block Height",
@ -285,56 +285,56 @@
"wchange56": "WARNING!", "wchange56": "WARNING!",
"wchange57": "Memo" "wchange57": "Memo"
}, },
"tradepage":{ "tradepage": {
"tchange1":"Trade Portal", "tchange1": "Trade Portal",
"tchange2":"Select Trading Pair", "tchange2": "Select Trading Pair",
"tchange3":"HISTORIC MARKET TRADES", "tchange3": "HISTORIC MARKET TRADES",
"tchange4":"MY TRADE HISTORY", "tchange4": "MY TRADE HISTORY",
"tchange5":"OPEN MARKET SELL ORDERS", "tchange5": "OPEN MARKET SELL ORDERS",
"tchange6":"MY ORDERS", "tchange6": "MY ORDERS",
"tchange7":"Stuck Offers", "tchange7": "Stuck Offers",
"tchange8":"Amount", "tchange8": "Amount",
"tchange9":"Price", "tchange9": "Price",
"tchange10":"Total", "tchange10": "Total",
"tchange11":"Date", "tchange11": "Date",
"tchange12":"Status", "tchange12": "Status",
"tchange13":"Seller", "tchange13": "Seller",
"tchange14":"Price Each", "tchange14": "Price Each",
"tchange15":"Clear Form", "tchange15": "Clear Form",
"tchange16":"You have", "tchange16": "You have",
"tchange17":"Action", "tchange17": "Action",
"tchange18":"BUY", "tchange18": "BUY",
"tchange19":"SELL", "tchange19": "SELL",
"tchange20":"Failed to Create Trade. Try again!", "tchange20": "Failed to Create Trade. Try again!",
"tchange21":"Failed to Create Trade. Error Code", "tchange21": "Failed to Create Trade. Error Code",
"tchange22":"Insufficient Funds!", "tchange22": "Insufficient Funds!",
"tchange23":"Buy Request Successful!", "tchange23": "Buy Request Successful!",
"tchange24":"Buy Request Existing!", "tchange24": "Buy Request Existing!",
"tchange25":"Failed to Create Trade. Error Code", "tchange25": "Failed to Create Trade. Error Code",
"tchange26":"Trade Cancelling In Progress!", "tchange26": "Trade Cancelling In Progress!",
"tchange27":"Failed to Cancel Trade. Try again!", "tchange27": "Failed to Cancel Trade. Try again!",
"tchange28":"Failed to Cancel Trade. Error Code", "tchange28": "Failed to Cancel Trade. Error Code",
"tchange29":"CANCEL", "tchange29": "CANCEL",
"tchange30":"Failed to Fetch Balance. Try again!", "tchange30": "Failed to Fetch Balance. Try again!",
"tchange31":"SOLD", "tchange31": "SOLD",
"tchange32":"BOUGHT", "tchange32": "BOUGHT",
"tchange33":"Average", "tchange33": "Average",
"tchange34":"Amount can not be 0", "tchange34": "Amount can not be 0",
"tchange35":"Price can not be 0", "tchange35": "Price can not be 0",
"tchange36":"PENDING AUTO BUY", "tchange36": "PENDING AUTO BUY",
"tchange37":"No auto buy order found !", "tchange37": "No auto buy order found !",
"tchange38":"ADD", "tchange38": "ADD",
"tchange39":"AUTO BUY ORDER", "tchange39": "AUTO BUY ORDER",
"tchange40":"Price", "tchange40": "Price",
"tchange41":"Successfully removed auto buy order!", "tchange41": "Successfully removed auto buy order!",
"tchange42":"MARKET OPEN SELL ORDERS", "tchange42": "MARKET OPEN SELL ORDERS",
"tchange43":"MY BUY HISTORY", "tchange43": "MY BUY HISTORY",
"tchange44":"Successfully added auto buy order!", "tchange44": "Successfully added auto buy order!",
"tchange45":"AUTO BUY WITH", "tchange45": "AUTO BUY WITH",
"tchange46":"AUTO BUY", "tchange46": "AUTO BUY",
"tchange47":"Sell for this price", "tchange47": "Sell for this price",
"tchange48":"NOT ENOUGH", "tchange48": "NOT ENOUGH",
"tchange49":"Price Chart" "tchange49": "Price Chart"
}, },
"rewardsharepage": { "rewardsharepage": {
"rchange1": "Rewardshares", "rchange1": "Rewardshares",
@ -565,7 +565,10 @@
"cchange56": "Transaction Failed!", "cchange56": "Transaction Failed!",
"cchange57": "User Info", "cchange57": "User Info",
"cchange58": "SEND MESSAGE", "cchange58": "SEND MESSAGE",
"cchange59": "TIP USER" "cchange59": "TIP USER",
"cchange60": "Group Invites Pending",
"cchange61": "Error when fetching group invites. Please try again!",
"cchange62": "Wrong Username and Address Inputted! Please try again!"
}, },
"welcomepage": { "welcomepage": {
"wcchange1": "Welcome to Q-Chat", "wcchange1": "Welcome to Q-Chat",
@ -792,67 +795,67 @@
"exp20": "Received", "exp20": "Received",
"exp21": "Trades" "exp21": "Trades"
}, },
"managegroup":{ "managegroup": {
"mg1":"Group Members", "mg1": "Group Members",
"mg2":"Invite To Group", "mg2": "Invite To Group",
"mg3":"Group Admins", "mg3": "Group Admins",
"mg4":"Update Group", "mg4": "Update Group",
"mg5":"Close Manage Group", "mg5": "Close Manage Group",
"mg6":"BAN", "mg6": "BAN",
"mg7":"KICK", "mg7": "KICK",
"mg8":"Group ID", "mg8": "Group ID",
"mg9":"Joined", "mg9": "Joined",
"mg10":"Add Group Admin", "mg10": "Add Group Admin",
"mg11":"Are you sure to add this member to admins ?", "mg11": "Are you sure to add this member to admins ?",
"mg12":"On pressing confirm, add admin request will be sent!", "mg12": "On pressing confirm, add admin request will be sent!",
"mg13":"Remove Group Admin", "mg13": "Remove Group Admin",
"mg14":"Remove Admin Address", "mg14": "Remove Admin Address",
"mg15":"Are you sure to remove this member from admins ?", "mg15": "Are you sure to remove this member from admins ?",
"mg16":"On pressing confirm, remove admin request will be sent!", "mg16": "On pressing confirm, remove admin request will be sent!",
"mg17":"Ban Member From Group", "mg17": "Ban Member From Group",
"mg18":"Member Name", "mg18": "Member Name",
"mg19":"Member Address", "mg19": "Member Address",
"mg20":"How Long To Ban", "mg20": "How Long To Ban",
"mg21":"Reason For Ban", "mg21": "Reason For Ban",
"mg22":"Are you sure to ban this member from the group ?", "mg22": "Are you sure to ban this member from the group ?",
"mg23":"On pressing confirm, the ban request will be sent!", "mg23": "On pressing confirm, the ban request will be sent!",
"mg24":"FOREVER", "mg24": "FOREVER",
"mg25":"Banned Members", "mg25": "Banned Members",
"mg26":"CANCEL BAN", "mg26": "CANCEL BAN",
"mg27":"Ban Expiry", "mg27": "Ban Expiry",
"mg28":"Cancel Ban Member From Group", "mg28": "Cancel Ban Member From Group",
"mg29":"Are you sure to cancel the ban for this member from the group ?", "mg29": "Are you sure to cancel the ban for this member from the group ?",
"mg30":"On pressing confirm, the cancel ban request will be sent!", "mg30": "On pressing confirm, the cancel ban request will be sent!",
"mg31":"Kick Member From Group", "mg31": "Kick Member From Group",
"mg32":"Reason For Kick", "mg32": "Reason For Kick",
"mg33":"Are you sure to kick this member from the group ?", "mg33": "Are you sure to kick this member from the group ?",
"mg34":"On pressing confirm, the kick request will be sent!", "mg34": "On pressing confirm, the kick request will be sent!",
"mg35":"No Open Group Invites", "mg35": "No Open Group Invites",
"mg36":"Your Open Group Invites", "mg36": "Your Open Group Invites",
"mg37":"Address or name to invite", "mg37": "Address or name to invite",
"mg38":"Invite Expiry Time", "mg38": "Invite Expiry Time",
"mg39":"All Fields Are Required", "mg39": "All Fields Are Required",
"mg40":"Are you sure to invite this member to the group ?", "mg40": "Are you sure to invite this member to the group ?",
"mg41":"On pressing confirm, the invite request will be sent!", "mg41": "On pressing confirm, the invite request will be sent!",
"mg42":"Group Type", "mg42": "Group Type",
"mg43":"Invite Expiry", "mg43": "Invite Expiry",
"mg44":"Public Group", "mg44": "Public Group",
"mg45":"Private Group", "mg45": "Private Group",
"mg46":"Cancel Invite", "mg46": "Cancel Invite",
"mg47":"Cancel Invite To Group", "mg47": "Cancel Invite To Group",
"mg48":"Are you sure to cancel the invite for this member ?", "mg48": "Are you sure to cancel the invite for this member ?",
"mg49":"On pressing confirm, the cancel invite request will be sent!", "mg49": "On pressing confirm, the cancel invite request will be sent!",
"mg50":"Coming Soon...", "mg50": "Coming Soon...",
"mg51":"Minimum 3 Characters / Maximum 32 Characters", "mg51": "Minimum 3 Characters / Maximum 32 Characters",
"mg52":"Maximum 128 Characters", "mg52": "Maximum 128 Characters",
"mg53":"Your Open Join Requests", "mg53": "Your Open Join Requests",
"mg54":"No Open Join Requests", "mg54": "No Open Join Requests",
"mg55":"Are you sure to accept the join request from this member ?", "mg55": "Are you sure to accept the join request from this member ?",
"mg56":"On pressing confirm, the accept join request will be sent!", "mg56": "On pressing confirm, the accept join request will be sent!",
"mg57":"Join Request Successfully Accepted", "mg57": "Join Request Successfully Accepted",
"mg58":"SOMETHING WENT WRONG", "mg58": "SOMETHING WENT WRONG",
"mg59":"Cancel Join Request Successfully Accepted", "mg59": "Cancel Join Request Successfully Accepted",
"mg60":"Are you sure to cancel the join request from this member ?", "mg60": "Are you sure to cancel the join request from this member ?",
"mg61":"On pressing confirm, the cancel join request will be sent!" "mg61": "On pressing confirm, the cancel join request will be sent!"
} }
} }

View File

@ -229,9 +229,9 @@ class ChatGroupsManagement extends LitElement {
render() { render() {
return html` return html`
<vaadin-icon @click=${()=> { <!-- <vaadin-icon @click=${()=> {
this.isOpenLeaveModal = true this.isOpenLeaveModal = true
}} class="top-bar-icon" style="margin: 0px 20px" icon="vaadin:exit" slot="icon"></vaadin-icon> }} class="top-bar-icon" style="margin: 0px 20px" icon="vaadin:exit" slot="icon"></vaadin-icon> -->
<!-- Leave Group Dialog --> <!-- Leave Group Dialog -->
<wrapper-modal <wrapper-modal
.removeImage=${() => { .removeImage=${() => {

View File

@ -1061,8 +1061,10 @@ class ChatPage extends LitElement {
id="sendTo" id="sendTo"
placeholder="${translate("chatpage.cchange7")}" placeholder="${translate("chatpage.cchange7")}"
@keydown=${() => { @keydown=${() => {
this.forwardActiveChatHeadUrl = {}; if (this.forwardActiveChatHeadUrl.selected) {
this.requestUpdate(); this.forwardActiveChatHeadUrl = {};
this.requestUpdate();
}
} }
} }
/> />
@ -1234,7 +1236,8 @@ class ChatPage extends LitElement {
const nameValue = this.shadowRoot.getElementById('sendTo').value; const nameValue = this.shadowRoot.getElementById('sendTo').value;
if (!nameValue) { if (!nameValue) {
this.userFound = []; this.userFound = [];
this.userFoundModalOpen = true; this.userFoundModalOpen = false;
this.loading = false;
return; return;
} }
try { try {
@ -1244,6 +1247,7 @@ class ChatPage extends LitElement {
}) })
if (result.error === 401) { if (result.error === 401) {
this.userFound = []; this.userFound = [];
this.loading = false;
} else { } else {
this.userFound = [ this.userFound = [
...this.userFound, ...this.userFound,
@ -1252,6 +1256,7 @@ class ChatPage extends LitElement {
} }
this.userFoundModalOpen = true; this.userFoundModalOpen = true;
} catch (error) { } catch (error) {
this.loading = false;
console.error(error); console.error(error);
let err4string = get("chatpage.cchange35"); let err4string = get("chatpage.cchange35");
parentEpml.request('showSnackBar', `${err4string}`) parentEpml.request('showSnackBar', `${err4string}`)
@ -1479,23 +1484,23 @@ class ChatPage extends LitElement {
} }
} }
async getName (recipient) { async getName (recipient) {
try { try {
const getNames = await parentEpml.request("apiCall", { const getNames = await parentEpml.request("apiCall", {
type: "api", type: "api",
url: `/names/address/${recipient}`, url: `/names/address/${recipient}`,
}); });
if (Array.isArray(getNames) && getNames.length > 0 ) { if (Array.isArray(getNames) && getNames.length > 0 ) {
return getNames[0].name return getNames[0].name
} else { } else {
return '' return ''
}
} catch (error) {
return ""
} }
} catch (error) {
return ""
} }
}
async renderPlaceholder() { async renderPlaceholder() {
const getName = async (recipient)=> { const getName = async (recipient)=> {
@ -2403,9 +2408,9 @@ async getName (recipient) {
}; };
if (this.forwardActiveChatHeadUrl.url) { if (this.forwardActiveChatHeadUrl.url) {
const activeChatHeadAddress = this.forwardActiveChatHeadUrl.url.split('/')[1] const activeChatHeadAddress = this.forwardActiveChatHeadUrl.url.split('/')[1];
try { try {
const res = await parentEpml.request('apiCall', { const res = await parentEpml.request('apiCall', {
type: 'api', type: 'api',
url: `/addresses/publickey/${activeChatHeadAddress}` url: `/addresses/publickey/${activeChatHeadAddress}`
}) })
@ -2425,21 +2430,58 @@ async getName (recipient) {
} }
} }
if (!this.forwardActiveChatHeadUrl && this.shadowRoot.getElementById("sendTo").value !== "") { if (!this.forwardActiveChatHeadUrl.selected && this.shadowRoot.getElementById("sendTo").value !== "") {
const userInput = this.shadowRoot.getElementById("sendTo").value.trim();
try { try {
const res = await parentEpml.request('apiCall', { let userPubkey = "";
const validatedAddress = await parentEpml.request('apiCall', {
type: 'api', type: 'api',
url: `/addresses/publickey/${this.shadowRoot.getElementById("sendTo").value}` url: `/addresses/validate/${userInput}`
}) });
if (res.error === 102) {
publicKey.key = '' const validatedUsername = await parentEpml.request('apiCall', {
publicKey.hasPubKey = false type: 'api',
} else if (res !== false) { url: `/names/${userInput}`
publicKey.key = res });
publicKey.hasPubKey = true
if (!validatedAddress && validatedUsername) {
userPubkey = await parentEpml.request('apiCall', {
type: 'api',
url: `/addresses/publickey/${validatedUsername.owner}`
});
this.forwardActiveChatHeadUrl = {
...this.forwardActiveChatHeadUrl,
url: `direct/${validatedUsername.owner}`,
name: validatedUsername.name,
selected: true
};
} else if (validatedAddress && !validatedUsername.name) {
userPubkey = await parentEpml.request('apiCall', {
type: 'api',
url: `/addresses/publickey/${userInput}`
});
this.forwardActiveChatHeadUrl = {
...this.forwardActiveChatHeadUrl,
url: `direct/${userInput}`,
name: "",
selected: true
};
} else if (!validatedAddress && !validatedUsername.name) {
let err4string = get("chatpage.cchange62");
parentEpml.request('showSnackBar', `${err4string}`);
getSendChatResponse(false);
return;
}
if (userPubkey.error === 102) {
publicKey.key = '';
publicKey.hasPubKey = false;
} else if (userPubkey !== false) {
publicKey.key = userPubkey;
publicKey.hasPubKey = true;
} else { } else {
publicKey.key = '' publicKey.key = '';
publicKey.hasPubKey = false publicKey.hasPubKey = false;
} }
} catch (error) { } catch (error) {
console.error(error); console.error(error);
@ -2454,9 +2496,9 @@ async getName (recipient) {
if (isRecipient === true) { if (isRecipient === true) {
if(!publicKey.hasPubKey){ if(!publicKey.hasPubKey){
let err4string = get("chatpage.cchange39"); let err4string = get("chatpage.cchange39");
parentEpml.request('showSnackBar', `${err4string}`) parentEpml.request('showSnackBar', `${err4string}`);
getSendChatResponse(false) getSendChatResponse(false);
return return;
} }
let chatResponse = await parentEpml.request('chat', { let chatResponse = await parentEpml.request('chat', {
type: 18, type: 18,
@ -2536,7 +2578,7 @@ async getName (recipient) {
if (response === true) { if (response === true) {
this.chatEditor.resetValue(); this.chatEditor.resetValue();
this.chatEditorNewChat.resetValue() this.chatEditorNewChat.resetValue()
if(isForward){ if (isForward) {
let successString = get("blockpage.bcchange15"); let successString = get("blockpage.bcchange15");
parentEpml.request('showSnackBar', `${successString}`); parentEpml.request('showSnackBar', `${successString}`);
} }
@ -2545,6 +2587,8 @@ async getName (recipient) {
} else { } else {
let err2string = get("chatpage.cchange21"); let err2string = get("chatpage.cchange21");
parentEpml.request('showSnackBar', `${err2string}`); parentEpml.request('showSnackBar', `${err2string}`);
this.forwardActiveChatHeadUrl = {};
this.shadowRoot.getElementById("sendTo").value = "";
} }
this.isLoading = false; this.isLoading = false;

View File

@ -62,7 +62,7 @@ export class UserInfo extends LitElement {
render() { render() {
let avatarImg = ""; let avatarImg = "";
if (this.selectedHead.name) { if (this.selectedHead && this.selectedHead.name) {
const myNode = window.parent.reduxStore.getState().app.nodeConfig.knownNodes[window.parent.reduxStore.getState().app.nodeConfig.node]; const myNode = window.parent.reduxStore.getState().app.nodeConfig.knownNodes[window.parent.reduxStore.getState().app.nodeConfig.node];
const nodeUrl = myNode.protocol + '://' + myNode.domain + ':' + myNode.port; const nodeUrl = myNode.protocol + '://' + myNode.domain + ':' + myNode.port;
const avatarUrl = `${nodeUrl}/arbitrary/THUMBNAIL/${this.selectedHead.name}/qortal_avatar?async=true&apiKey=${myNode.apiKey}`; const avatarUrl = `${nodeUrl}/arbitrary/THUMBNAIL/${this.selectedHead.name}/qortal_avatar?async=true&apiKey=${myNode.apiKey}`;
@ -85,7 +85,7 @@ export class UserInfo extends LitElement {
${avatarImg} ${avatarImg}
</div>` : </div>` :
html``} html``}
${!this.isImageLoaded && this.selectedHead.name ? ${!this.isImageLoaded && this.selectedHead && this.selectedHead.name ?
html` html`
<div class="avatar-container"> <div class="avatar-container">
<div class="user-info-no-avatar"> <div class="user-info-no-avatar">
@ -94,16 +94,14 @@ export class UserInfo extends LitElement {
</div> </div>
` `
: ""} : ""}
${!this.isImageLoaded && !this.selectedHead.name ? ${!this.isImageLoaded && this.selectedHead && !this.selectedHead.name ?
html` html`
<div <div class="avatar-container">
class="avatar-container"
>
<img src="/img/qortal-chat-logo.png" alt="avatar" /> <img src="/img/qortal-chat-logo.png" alt="avatar" />
</div>` </div>`
: ""} : ""}
<div class="user-info-header"> <div class="user-info-header">
${this.selectedHead.name ? this.selectedHead.name : cropAddress(this.selectedHead.address)} ${this.selectedHead && this.selectedHead.name ? this.selectedHead.name : this.selectedHead ? cropAddress(this.selectedHead.address) : null}
</div> </div>
<div <div
class="send-message-button" class="send-message-button"

View File

@ -54,10 +54,103 @@ export const qchatStyles = css`
position: absolute; position: absolute;
bottom: 0; bottom: 0;
width: 20vw; width: 20vw;
height: 60px;
background: var(--white); background: var(--white);
border-top: 1px solid var(--border); border-top: 1px solid var(--border);
border-right: 3px #ddd solid; border-right: 3px #ddd solid;
display: flex;
justify-content: space-between;
gap: 15px;
flex-direction: column;
padding: 5px 30px 0 30px;
}
.groups-button-container {
position: relative;
}
.groups-button {
width: 100%;
background-color: rgb(116, 69, 240);
border: none;
color: white;
font-weight: bold;
font-family: 'Roboto';
letter-spacing: 0.8px;
height: 100%;
display: flex;
align-items: center;
justify-content: center;
border-radius: 5px;
gap: 10px;
padding: 5px 8px;
transition: all 0.1s ease-in-out;
}
.groups-button-notif {
position: absolute;
top: -10px;
right: -8px;
width: 25px;
border-radius: 50%;
height: 25px;
font-weight: bold;
display: flex;
align-items: center;
justify-content: center;
font-family: Montserrat, sans-serif;
font-size: 16px;
font-weight: bold;
color: black;
background-color: rgb(51, 213, 0);
user-select: none;
transition: all 0.3s ease-in-out 0s;
}
.groups-button-notif:hover {
cursor: auto;
box-shadow: rgba(99, 99, 99, 0.2) 0px 2px 8px 0px;
}
.groups-button-notif:hover + .groups-button-notif-number {
display: block;
opacity: 1;
animation: fadeIn 0.6s;
}
@keyframes fadeIn {
from {
opacity: 0;
top: -10px;
}
to {
opacity: 1;
top: -60px;
}
}
.groups-button-notif-number {
position: absolute;
transform: translateX(-50%);
left: 50%;
width: 150px;
text-align: center;
border-radius: 3px;
padding: 5px 10px;
background-color: white;
color: black;
font-family: Roboto, sans-serif;
letter-spacing: 0.3px;
font-weight: 300;
display: none;
opacity: 0;
top: -60px;
box-shadow: rgb(216 216 216 / 25%) 0px 6px 12px -2px, rgb(0 0 0 / 30%) 0px 3px 7px -3px;
}
.groups-button:hover {
cursor: pointer;
filter: brightness(120%);
} }
.people-list .search { .people-list .search {

View File

@ -47,7 +47,8 @@ class Chat extends LitElement {
openPrivateMessage: { type: Boolean }, openPrivateMessage: { type: Boolean },
userFound: { type: Array}, userFound: { type: Array},
userFoundModalOpen: { type: Boolean }, userFoundModalOpen: { type: Boolean },
userSelected: { type: Object } userSelected: { type: Object },
groupInvites: { type: Array }
} }
} }
@ -86,13 +87,14 @@ class Chat extends LitElement {
this.userFound = [] this.userFound = []
this.userFoundModalOpen = false this.userFoundModalOpen = false
this.userSelected = {} this.userSelected = {}
this.groupInvites = []
} }
async setActiveChatHeadUrl(url) { async setActiveChatHeadUrl(url) {
this.activeChatHeadUrl = '' this.activeChatHeadUrl = ''
await this.updateComplete; await this.updateComplete;
this.activeChatHeadUrl = url this.activeChatHeadUrl = url
} }
render() { render() {
return html` return html`
@ -109,9 +111,30 @@ class Chat extends LitElement {
${this.isEmptyArray(this.chatHeads) ? this.renderLoadingText() : this.renderChatHead(this.chatHeads)} ${this.isEmptyArray(this.chatHeads) ? this.renderLoadingText() : this.renderChatHead(this.chatHeads)}
</ul> </ul>
<div class="blockedusers"> <div class="blockedusers">
<div class="center"> <div class="groups-button-container">
<mwc-button raised label="${translate("chatpage.cchange3")}" icon="person_off" @click=${() => this.shadowRoot.querySelector('#blockedUserDialog').show()}></mwc-button> <a href="/app/group-management">
<button class="groups-button">
<mwc-icon>groups</mwc-icon>
${translate("sidemenu.groupmanagement")}
</button>
</a>
${this.groupInvites.length > 0 ? (
html`
<div class="groups-button-notif">
${this.groupInvites.length}
</div>
<div class="groups-button-notif-number">
${this.groupInvites.length} ${translate("chatpage.cchange60")}
</div>
`
) : null}
</div> </div>
<mwc-button
raised
label="${translate("chatpage.cchange3")}"
icon="person_off"
@click=${() => this.shadowRoot.querySelector('#blockedUserDialog').show()}>
</mwc-button>
</div> </div>
</div> </div>
<div class="chat"> <div class="chat">
@ -271,11 +294,12 @@ class Chat extends LitElement {
` `
} }
firstUpdated() { async firstUpdated() {
this.changeLanguage() this.changeLanguage();
this.changeTheme() this.changeTheme();
this.getChatBlockedList() this.getChatBlockedList();
this.getLocalBlockedList() this.getLocalBlockedList();
await this.getPendingGroupInvites();
const getBlockedUsers = async () => { const getBlockedUsers = async () => {
let blockedUsers = await parentEpml.request('apiCall', { let blockedUsers = await parentEpml.request('apiCall', {
@ -672,6 +696,20 @@ class Chat extends LitElement {
}) })
} }
async getPendingGroupInvites() {
const myAddress = window.parent.reduxStore.getState().app.selectedAddress.address
try {
let pendingGroupInvites = await parentEpml.request('apiCall', {
url: `/groups/invites/${myAddress}`
})
this.groupInvites = pendingGroupInvites;
} catch (error) {
console.error(error);
let err4string = get("chatpage.cchange61");
parentEpml.request('showSnackBar', `${err4string}`)
}
}
async unblockUser(websiteObj) { async unblockUser(websiteObj) {
let owner = websiteObj.owner let owner = websiteObj.owner