Skip to content

Commit

Permalink
Merge branch 'wevote:develop' into develop
Browse files Browse the repository at this point in the history
  • Loading branch information
fdiazq authored Oct 2, 2024
2 parents 03cc7fb + a682606 commit e47a568
Show file tree
Hide file tree
Showing 5 changed files with 235 additions and 40 deletions.
9 changes: 7 additions & 2 deletions src/js/common/actions/ChallengeInviteeActions.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,17 @@ export default {
});
},

challengeInviteeSave (challengeWeVoteId, inviteeName) {
console.log('challengeInviteeSave called with challengeWeVoteId: ', challengeWeVoteId, ' and inviteeName: ', inviteeName);
challengeInviteeSave (challengeWeVoteId, inviteeName = '', inviteeNameChanged = false, inviteTextFromInviter = '', inviteTextFromInviterChanged = false, inviteeUrlCode = '', inviteeUrlCodeChanged = false) {
// console.log('challengeInviteeSave called with challengeWeVoteId: ', challengeWeVoteId, ' and inviteeName: ', inviteeName);
Dispatcher.loadEndpoint('challengeInviteeSave',
{
challenge_we_vote_id: challengeWeVoteId,
invitee_name: inviteeName,
invitee_name_changed: inviteeNameChanged,
invitee_text_from_inviter: inviteTextFromInviter,
invitee_text_from_inviter_changed: inviteTextFromInviterChanged,
invitee_url_code: inviteeUrlCode,
invitee_url_code_changed: inviteeUrlCodeChanged,
});
},

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,20 +2,110 @@ import { Button, FormControl, TextField } from '@mui/material';
import styled from 'styled-components';
import withStyles from '@mui/styles/withStyles';
import PropTypes from 'prop-types';
import React from 'react';
import React, { Suspense } from 'react';
import CopyToClipboard from 'react-copy-to-clipboard';
import { renderLog } from '../../utils/logging';
import ChallengeInviteeActions from '../../actions/ChallengeInviteeActions';
import ChallengeInviteeStore from '../../stores/ChallengeInviteeStore';
import ChallengeParticipantStore from '../../stores/ChallengeParticipantStore';
import ChallengeStore from '../../stores/ChallengeStore';

const ChallengeParticipantFirstRetrieveController = React.lazy(() => import(/* webpackChunkName: 'ChallengeParticipantFirstRetrieveController' */ '../ChallengeParticipant/ChallengeParticipantFirstRetrieveController'));

const InviteFriendToChallengeInput = ({ classes, challengeWeVoteId, externalUniqueId }) => {
renderLog('InviteFriendToChallengeInputBox'); // Set LOG_RENDER_EVENTS to log all renders
const [friendName, setFriendName] = React.useState([]);
const [challengeInviteTextDefault, setChallengeInviteTextDefault] = React.useState('');
const [challengeTitle, setChallengeTitle] = React.useState('');
const [inviteCopiedMessageOn, setInviteCopiedMessageOn] = React.useState(false);
const [inviteeName, setInviteeName] = React.useState('');
const [inviteTextForFriends, setInviteTextForFriends] = React.useState('');
const [inviteTextToSend, setInviteTextToSend] = React.useState('');
// const [urlToSend, setUrlToSend] = React.useState('');

function prepareInviteTextToSend () {
const inviteeFirstName = inviteeName.split(' ')[0];
const inviterFirstName = 'David';
const inviteTextToSendTemp1 = `Hi ${inviteeFirstName}, this is ${inviterFirstName}. `;
const inviteTextToSendTemp2 = inviteTextForFriends || challengeInviteTextDefault;
const inviteeUrlCode = ChallengeInviteeStore.getNextInviteeUrlCode();
const urlToSendTemp = `${ChallengeStore.getSiteUrl(challengeWeVoteId)}/++/${inviteeUrlCode}`;
const inviteTextToSendTemp3 = `${inviteTextToSendTemp1}${inviteTextToSendTemp2} ${urlToSendTemp}`;
setInviteTextToSend(inviteTextToSendTemp3);
// setUrlToSend(urlToSendTemp);
}

function resetForm () {
setInviteeName('');
setTimeout(() => {
prepareInviteTextToSend();
}, 250);
}

const handleShare = async () => {
const inviteeUrlCode = ChallengeInviteeStore.getNextInviteeUrlCode();
ChallengeInviteeActions.challengeInviteeSave(challengeWeVoteId, inviteeName, true, inviteTextToSend, true, inviteeUrlCode, true);
setInviteCopiedMessageOn(true);
setTimeout(() => {
console.log('handleShare setTimeout fired');
setInviteCopiedMessageOn(false);
resetForm();
}, 1000);
if (navigator.share) {
try {
await navigator.share({
title: challengeTitle,
text: inviteTextToSend,
// url: urlToSend,
});
console.log('Content shared successfully!');
} catch (error) {
console.error('Error sharing:', error);
}
} else {
console.log('Web Share API is not supported on this browser.');
// Fallback to a custom share modal or other sharing methods
}
};

function setFriendNameFromEvent (event) {
if (event.target.name === 'friendNameTextField') {
setFriendName(event.target.value);
function setInviteeNameFromEvent (event) {
if (event.target.name === 'inviteeNameTextField') {
setInviteeName(event.target.value);
prepareInviteTextToSend();
}
}

React.useEffect(() => {
const onChallengeInviteeStoreChange = () => {
console.log('InviteeStore change');
prepareInviteTextToSend();
};

const onChallengeParticipantStoreChange = () => {
setInviteTextForFriends(ChallengeParticipantStore.getInviteTextForFriends(challengeWeVoteId));
prepareInviteTextToSend();
};

const onChallengeStoreChange = () => {
setChallengeInviteTextDefault(ChallengeStore.getChallengeInviteTextDefaultByWeVoteId(challengeWeVoteId));
setChallengeTitle(ChallengeStore.getChallengeTitleByWeVoteId(challengeWeVoteId));
prepareInviteTextToSend();
};

// console.log('Fetching participants for:', challengeWeVoteId);
const challengeInviteeStoreListener = ChallengeInviteeStore.addListener(onChallengeInviteeStoreChange);
onChallengeParticipantStoreChange();
const challengeParticipantStoreListener = ChallengeParticipantStore.addListener(onChallengeParticipantStoreChange);
onChallengeParticipantStoreChange();
const challengeStoreListener = ChallengeStore.addListener(onChallengeStoreChange);
onChallengeStoreChange();

return () => {
challengeInviteeStoreListener.remove();
challengeParticipantStoreListener.remove();
challengeStoreListener.remove();
};
}, [challengeWeVoteId]);

return (
<InviteFriendToChallengeInputWrapper>
<form onSubmit={(e) => { e.preventDefault(); }}>
Expand All @@ -25,33 +115,48 @@ const InviteFriendToChallengeInput = ({ classes, challengeWeVoteId, externalUniq
<TextField
// classes={{ root: classes.textField }} // Not working yet
id={`campaignTitleTextArea-${externalUniqueId}`}
name="friendNameTextField"
name="inviteeNameTextField"
margin="dense"
value={inviteeName}
variant="outlined"
placeholder="Your friend's name"
onChange={setFriendNameFromEvent} // eslint-disable-line react/jsx-no-bind
onChange={setInviteeNameFromEvent} // eslint-disable-line react/jsx-no-bind
/>
</FormControl>
</ColumnFullWidth>
</Wrapper>
</form>
<InviteFriendButtonOuterWrapper>
<InviteFriendButtonInnerWrapper>
<Button
classes={{ root: classes.buttonDesktop }}
color="primary"
id="inviteToChallengeNow"
onClick={() => ChallengeInviteeActions.challengeInviteeSave(challengeWeVoteId, friendName)}
variant="contained"
>
Invite
{' '}
{`${friendName || 'friend'}`}
{' '}
to challenge
</Button>
{/* onCopy={this.copyLink} */}
<CopyToClipboard text={inviteTextToSend}>
<Button
classes={{ root: classes.buttonDesktop }}
color="primary"
id="inviteToChallengeNow"
onClick={() => handleShare()}
variant="contained"
>
{inviteCopiedMessageOn ? (
<span>
Invite copied!
</span>
) : (
<span>
Invite
{' '}
{`${inviteeName || 'friend'}`}
{' '}
to challenge
</span>
)}
</Button>
</CopyToClipboard>
</InviteFriendButtonInnerWrapper>
</InviteFriendButtonOuterWrapper>
<Suspense fallback={<span>&nbsp;</span>}>
<ChallengeParticipantFirstRetrieveController challengeWeVoteId={challengeWeVoteId} />
</Suspense>
</InviteFriendToChallengeInputWrapper>
);
};
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,16 +26,20 @@ const ChallengeInviteeListRoot = ({ challengeWeVoteId, classes }) => {
const [inviteeList, setInviteeList] = React.useState([]);

const onChallengeInviteeStoreChange = () => {
setInviteeList(ChallengeInviteeStore.getChallengeInviteeList(challengeWeVoteId));
// console.log('ChallengeInviteeStoreChange');
const incomingInviteeList = ChallengeInviteeStore.getChallengeInviteeList(challengeWeVoteId);
// console.log('ChallengeInviteeListRoot onChallengeInviteeStoreChange incomingInviteeList:', incomingInviteeList);
const incomingInviteeListNew = [...incomingInviteeList]; // So React detects this as a new list
setInviteeList(incomingInviteeListNew);
};

React.useEffect(() => {
// console.log('Fetching participants for:', challengeWeVoteId);
const storeListener = ChallengeInviteeStore.addListener(onChallengeInviteeStoreChange);
const challengeInviteeStoreListener = ChallengeInviteeStore.addListener(onChallengeInviteeStoreChange);
onChallengeInviteeStoreChange();

return () => {
storeListener.remove();
challengeInviteeStoreListener.remove();
};
}, [challengeWeVoteId]);
return (
Expand All @@ -45,8 +49,8 @@ const ChallengeInviteeListRoot = ({ challengeWeVoteId, classes }) => {
</Heading>
<ChallengeInviteeList
challengeWeVoteId={challengeWeVoteId}
// inviteeList={inviteeList}
inviteeList={inviteeListDummyData}
inviteeList={inviteeList}
// inviteeList={inviteeListDummyData}
/>
<Suspense fallback={<></>}>
<FirstChallengeInviteeListController challengeWeVoteId={challengeWeVoteId} searchText="SEARCH TEXT HERE" />
Expand Down
88 changes: 75 additions & 13 deletions src/js/common/stores/ChallengeInviteeStore.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ class ChallengeInviteeStore extends ReduceStore {
shareButtonClicked: false,
inviteeEndorsementQueuedToSave: '',
inviteeEndorsementQueuedToSaveSet: false,
nextInviteeUrlCode: '',
visibleToPublic: true, // Default setting
visibleToPublicQueuedToSave: true, // Default setting
visibleToPublicQueuedToSaveSet: false,
Expand Down Expand Up @@ -58,6 +59,19 @@ class ChallengeInviteeStore extends ReduceStore {
return this.getState().allCachedChallengeInviteeVoterEntries[challengeWeVoteId] || {};
}

getInviteTextFromInviter (challengeInviteeId) {
const challengeInvitee = this.getChallengeInviteeById(challengeInviteeId);
if ('invite_text_from_inviter' in challengeInvitee) {
return challengeInvitee.invite_text_from_inviter;
} else {
return '';
}
}

getNextInviteeUrlCode () {
return this.getState().nextInviteeUrlCode || '--';
}

getShareButtonClicked () {
return this.getState().shareButtonClicked;
}
Expand Down Expand Up @@ -117,17 +131,34 @@ class ChallengeInviteeStore extends ReduceStore {
return challengeInviteeGenericList;
}

mostRecentDateFromChallengeInvitee (challengeInvitee) {
let mostRecentDate = challengeInvitee.date_invite_sent;
if (challengeInvitee.date_invite_viewed > mostRecentDate) {
mostRecentDate = challengeInvitee.date_invite_viewed;
}
if (challengeInvitee.date_challenge_joined > mostRecentDate) {
mostRecentDate = challengeInvitee.date_challenge_joined;
}
return mostRecentDate;
}

orderByMostRecentDate = (firstItem, secondItem) => new Date(secondItem.most_recent_date) - new Date(firstItem.most_recent_date);

reduce (state, action) {
const {
allCachedChallengeInvitees,
allChallengeInviteeLists,
} = state;
let {
latestChallengeInvitees,
latestChallengeInvitees, nextInviteeUrlCode,
} = state;
let challengeList;
let challengeInvitee;
let challengeInviteeTemp;
let challengeInviteeList;
let challengeInviteeListTemp = [];
let alreadyInList;
let mostRecentDate;

let revisedState;
switch (action.type) {
Expand Down Expand Up @@ -161,28 +192,59 @@ class ChallengeInviteeStore extends ReduceStore {
revisedState = state;
challengeInviteeList = action.res.challenge_invitee_list || [];
// console.log('challengeInviteeListRetrieve challenge_invitee_list:', challengeInviteeList);
allChallengeInviteeLists[action.res.challenge_we_vote_id] = challengeInviteeList;
challengeInviteeList.forEach((oneInvitee) => {
if (oneInvitee.invitee_id) {
allCachedChallengeInvitees[oneInvitee.invitee_id] = oneInvitee;
challengeInviteeListTemp = [];
challengeInviteeList.forEach((oneChallengeInvitee) => {
mostRecentDate = this.mostRecentDateFromChallengeInvitee(oneChallengeInvitee);
challengeInviteeTemp = oneChallengeInvitee;
challengeInviteeTemp.most_recent_date = mostRecentDate;
challengeInviteeListTemp.push(challengeInviteeTemp);
if (oneChallengeInvitee.invitee_id) {
allCachedChallengeInvitees[oneChallengeInvitee.invitee_id] = challengeInviteeTemp;
}
});
// console.log('challengeInviteeListRetrieve challengeInviteeListTemp:', challengeInviteeListTemp);
challengeInviteeListTemp = challengeInviteeListTemp.sort(this.orderByMostRecentDate);
allChallengeInviteeLists[action.res.challenge_we_vote_id] = challengeInviteeListTemp;
if (action.res.next_invitee_url_code) {
nextInviteeUrlCode = action.res.next_invitee_url_code;
revisedState = { ...revisedState, nextInviteeUrlCode };
}
revisedState = { ...revisedState, allCachedChallengeInvitees };
revisedState = { ...revisedState, allChallengeInviteeLists };
return revisedState;

case 'challengeInviteeSave':
console.log('ChallengeInviteeStore challengeInviteeSave');
if (!action.res || !action.res.success) return state;
if (action.res.challenge_we_vote_id && action.res.success) {
if (action.res.invitee_id) {
allCachedChallengeInvitees[action.res.invitee_id] = action.res;
revisedState = state;
challengeInvitee = action.res;
if (challengeInvitee.challenge_we_vote_id) {
if (challengeInvitee.invitee_id) {
mostRecentDate = this.mostRecentDateFromChallengeInvitee(challengeInvitee);
challengeInvitee.most_recent_date = mostRecentDate;
allCachedChallengeInvitees[challengeInvitee.invitee_id] = challengeInvitee;
revisedState = { ...revisedState, allCachedChallengeInvitees };
}
}
if (challengeInvitee.invitee_id) {
alreadyInList = false;
challengeInviteeList = allChallengeInviteeLists[challengeInvitee.challenge_we_vote_id];
challengeInviteeList.forEach((oneChallengeInvitee) => {
if (oneChallengeInvitee.invitee_id === challengeInvitee.invitee_id) {
alreadyInList = true;
}
});
if (!alreadyInList) {
challengeInviteeListTemp = allChallengeInviteeLists[challengeInvitee.challenge_we_vote_id];
challengeInviteeListTemp.unshift(action.res);
allChallengeInviteeLists[challengeInvitee.challenge_we_vote_id] = [...challengeInviteeListTemp];
revisedState = { ...revisedState, allChallengeInviteeLists };
}
}
return {
...state,
allCachedChallengeInvitees,
};
if (action.res.next_invitee_url_code) {
nextInviteeUrlCode = action.res.next_invitee_url_code;
revisedState = { ...revisedState, nextInviteeUrlCode };
}
return revisedState;

case 'inviteeEndorsementQueuedToSave':
// console.log('ChallengeInviteeStore inviteeEndorsementQueuedToSave: ', action.payload);
Expand Down
Loading

0 comments on commit e47a568

Please sign in to comment.