feat: whatsapp stories implementation (#3994)
* support sending message from status broadcast * add to index.d.ts * add method to contact * new modules * Update Utils.js * add for the examples * add color assertion function * finishing.. * added waveforms for audio messages and minor fixes * fix eslint * refactor reorganize the store to include additional modules. * adapt * the last one. --------- Co-authored-by: Rajeh Taher <rajeh@reforward.dev>
This commit is contained in:
parent
dec1bee842
commit
6aa1bd85ab
2 changed files with 152 additions and 12 deletions
|
|
@ -54,6 +54,7 @@ exports.ExposeStore = () => {
|
|||
window.Store.MediaObject = window.require('WAWebMediaStorage');
|
||||
window.Store.MediaTypes = window.require('WAWebMmsMediaTypes');
|
||||
window.Store.MediaUpload = window.require('WAWebMediaMmsV4Upload');
|
||||
window.Store.MediaUpdate = window.require('WAWebMediaUpdateMsg');
|
||||
window.Store.MsgKey = window.require('WAWebMsgKey');
|
||||
window.Store.OpaqueData = window.require('WAWebMediaOpaqueData');
|
||||
window.Store.QueryProduct = window.require('WAWebBizProductCatalogBridge');
|
||||
|
|
@ -77,7 +78,6 @@ exports.ExposeStore = () => {
|
|||
window.Store.PresenceUtils = window.require('WAWebPresenceChatAction');
|
||||
window.Store.ChatState = window.require('WAWebChatStateBridge');
|
||||
window.Store.findCommonGroups = window.require('WAWebFindCommonGroupsContactAction').findCommonGroups;
|
||||
window.Store.StatusUtils = window.require('WAWebContactStatusBridge');
|
||||
window.Store.ConversationMsgs = window.require('WAWebChatLoadMessages');
|
||||
window.Store.sendReactionToMsg = window.require('WAWebSendReactionMsgAction').sendReactionToMsg;
|
||||
window.Store.createOrUpdateReactionsModule = window.require('WAWebDBCreateOrUpdateReactions');
|
||||
|
|
@ -110,7 +110,7 @@ exports.ExposeStore = () => {
|
|||
window.Store.BusinessGatingUtils = window.require('WAWebBizGatingUtils');
|
||||
window.Store.PollsVotesSchema = window.require('WAWebPollsVotesSchema');
|
||||
window.Store.PollsSendVote = window.require('WAWebPollsSendVoteMsgAction');
|
||||
|
||||
|
||||
window.Store.Settings = {
|
||||
...window.require('WAWebUserPrefsGeneral'),
|
||||
...window.require('WAWebUserPrefsNotifications'),
|
||||
|
|
@ -200,6 +200,12 @@ exports.ExposeStore = () => {
|
|||
...window.require('WAWebSaveContactAction'),
|
||||
...window.require('WAWebDeleteContactAction')
|
||||
};
|
||||
window.Store.StatusUtils = {
|
||||
...window.require('WAWebContactStatusBridge'),
|
||||
...window.require('WAWebSendStatusMsgAction'),
|
||||
...window.require('WAWebRevokeStatusAction'),
|
||||
...window.require('WAWebStatusGatingUtils')
|
||||
};
|
||||
|
||||
if (!window.Store.Chat._find || !window.Store.Chat.findImpl) {
|
||||
window.Store.Chat._find = e => {
|
||||
|
|
|
|||
|
|
@ -22,10 +22,11 @@ exports.LoadUtils = () => {
|
|||
|
||||
window.WWebJS.sendMessage = async (chat, content, options = {}) => {
|
||||
const isChannel = window.Store.ChatGetters.getIsNewsletter(chat);
|
||||
const isStatus = window.Store.ChatGetters.getIsBroadcast(chat);
|
||||
|
||||
let mediaOptions = {};
|
||||
if (options.media) {
|
||||
mediaOptions = options.sendMediaAsSticker && !isChannel
|
||||
mediaOptions = options.sendMediaAsSticker && !isChannel && !isStatus
|
||||
? await window.WWebJS.processStickerData(options.media)
|
||||
: await window.WWebJS.processMediaData(options.media, {
|
||||
forceSticker: options.sendMediaAsSticker,
|
||||
|
|
@ -33,7 +34,8 @@ exports.LoadUtils = () => {
|
|||
forceVoice: options.sendAudioAsVoice,
|
||||
forceDocument: options.sendMediaAsDocument,
|
||||
forceMediaHd: options.sendMediaAsHd,
|
||||
sendToChannel: isChannel
|
||||
sendToChannel: isChannel,
|
||||
sendToStatus: isStatus
|
||||
});
|
||||
mediaOptions.caption = options.caption;
|
||||
content = options.sendMediaAsSticker ? undefined : mediaOptions.preview;
|
||||
|
|
@ -246,6 +248,10 @@ exports.LoadUtils = () => {
|
|||
participant = window.Store.WidFactory.asUserWidOrThrow(from);
|
||||
}
|
||||
|
||||
if (typeof chat.id?.isStatus === 'function' && chat.id.isStatus()) {
|
||||
participant = window.Store.WidFactory.asUserWidOrThrow(from);
|
||||
}
|
||||
|
||||
const newMsgKey = new window.Store.MsgKey({
|
||||
from: from,
|
||||
to: chat.id,
|
||||
|
|
@ -320,6 +326,37 @@ exports.LoadUtils = () => {
|
|||
return msg;
|
||||
}
|
||||
|
||||
if (isStatus) {
|
||||
const { backgroundColor, fontStyle } = extraOptions;
|
||||
const isMedia = Object.keys(mediaOptions).length > 0;
|
||||
const mediaUpdate = data => window.Store.MediaUpdate(data, mediaOptions);
|
||||
const msg = new window.Store.Msg.modelClass({
|
||||
...message,
|
||||
author: participant ? participant : null,
|
||||
messageSecret: window.crypto.getRandomValues(new Uint8Array(32)),
|
||||
cannotBeRanked: window.Store.StatusUtils.canCheckStatusRankingPosterGating()
|
||||
});
|
||||
|
||||
// for text only
|
||||
const statusOptions = {
|
||||
color: backgroundColor && window.WWebJS.assertColor(backgroundColor) || 0xff7acca5,
|
||||
font: fontStyle >= 0 && fontStyle <= 7 && fontStyle || 0,
|
||||
text: msg.body
|
||||
};
|
||||
|
||||
await window.Store.StatusUtils[
|
||||
isMedia ?
|
||||
'sendStatusMediaMsgAction' : 'sendStatusTextMsgAction'
|
||||
](
|
||||
...(
|
||||
isMedia ?
|
||||
[msg, mediaUpdate] : [statusOptions]
|
||||
)
|
||||
);
|
||||
|
||||
return msg;
|
||||
}
|
||||
|
||||
const [msgPromise, sendMsgResultPromise] = window.Store.SendMessage.addAndSendMsgToChat(chat, message);
|
||||
await msgPromise;
|
||||
|
||||
|
|
@ -407,7 +444,7 @@ exports.LoadUtils = () => {
|
|||
return stickerInfo;
|
||||
};
|
||||
|
||||
window.WWebJS.processMediaData = async (mediaInfo, { forceSticker, forceGif, forceVoice, forceDocument, forceMediaHd, sendToChannel }) => {
|
||||
window.WWebJS.processMediaData = async (mediaInfo, { forceSticker, forceGif, forceVoice, forceDocument, forceMediaHd, sendToChannel, sendToStatus }) => {
|
||||
const file = window.WWebJS.mediaInfoToFile(mediaInfo);
|
||||
const opaqueData = await window.Store.OpaqueData.createFromData(file, file.type);
|
||||
const mediaParams = {
|
||||
|
|
@ -434,7 +471,7 @@ exports.LoadUtils = () => {
|
|||
throw new Error('media-fault: sendToChat filehash undefined');
|
||||
}
|
||||
|
||||
if (forceVoice && mediaData.type === 'ptt') {
|
||||
if ((forceVoice && mediaData.type === 'ptt') || (sendToStatus && mediaData.type === 'audio')) {
|
||||
const waveform = mediaObject.contentInfo.waveform;
|
||||
mediaData.waveform =
|
||||
waveform || await window.WWebJS.generateWaveform(file);
|
||||
|
|
@ -463,7 +500,7 @@ exports.LoadUtils = () => {
|
|||
mimetype: mediaData.mimetype,
|
||||
mediaObject,
|
||||
mediaType,
|
||||
...(sendToChannel ? { calculateToken: window.Store.SendChannelMessage.getRandomFilehash } : {})
|
||||
...(sendToChannel ? { calculateToken: window.Store.SendChannelMessage.getRandomFilehash() } : {})
|
||||
};
|
||||
|
||||
const uploadedMedia = !sendToChannel
|
||||
|
|
@ -1165,4 +1202,20 @@ exports.LoadUtils = () => {
|
|||
|
||||
return { lid, phone };
|
||||
};
|
||||
|
||||
window.WWebJS.assertColor = (hex) => {
|
||||
let color;
|
||||
if (typeof hex === 'number') {
|
||||
color = hex > 0 ? hex : 0xffffffff + parseInt(hex) + 1;
|
||||
} else if (typeof hex === 'string') {
|
||||
let number = hex.trim().replace('#', '');
|
||||
if (number.length <= 6) {
|
||||
number = 'FF' + number.padStart(6, '0');
|
||||
}
|
||||
color = parseInt(number, 16);
|
||||
} else {
|
||||
throw 'Invalid hex color';
|
||||
}
|
||||
return color;
|
||||
};
|
||||
};
|
||||
|
|
|
|||
Loading…
Reference in a new issue