Haris
Haris

Reputation: 1

Audio doesn't play in Remotion and Nextjs

I am working on a youtube shorts automation website with remotion and nextjs and i am working a message story type videos and there are messages that are said by tts, but only the first audio can be heard and the other message isn't!

here is the page i play the video:

"use client"
import React from 'react'
import { Player } from "@remotion/player"
import { Video } from '@/remotion/fake-text/main';

interface Message {
  id: string;
  direction: 'left' | 'right';
  type: 'text' | 'image';
  content: string;
  soundEffect: string;
  ttsURL: string;
  conversationId: string;
}

interface Conversation {
  id: string;
  templateName: string;
  profilePicture: string;
  unreadMessagesCount: number;
  delay: number;
  borderRadius: number;
  scale: number;
  recieverName: string;
  useShadow: boolean;
  shadowColor: string;
  shadowSize: number;
  projectId: string;
  createdAt: string;
  updatedAt: string;
  messages: Message[];
}

interface ConversationsData {
  conversations: Conversation[];
}

const sampleData: ConversationsData = {
  conversations: [
    {
      id: "b45389f4-438a-45f1-bf96-c5bbe7d4e71b",
      templateName: "imessage-dark",
      profilePicture: "",
      unreadMessagesCount: 0,
      delay: 0,
      borderRadius: 15,
      scale: 100,
      recieverName: "Unknown",
      useShadow: true,
      shadowColor: "#000000",
      shadowSize: 12,
      projectId: "675a7f54-965f-4f91-86e0-1afde27857d0",
      createdAt: "2024-10-29T17:41:11.599Z",
      updatedAt: "2024-10-29T17:41:11.599Z",
      messages: [
        {
          id: "8b31ce27-eeb8-48d8-bb18-11920f4c85b0",
          direction: "left",
          type: "text",
          content: "Hello",
          soundEffect: "",
          ttsURL: "https://pub-d00f0faa09e4457e89f145c79e27b6c9.r2.dev/speeches/1730223668032-IKne3meq5aSn9XLyUdCD.mp3",
          conversationId: "b45389f4-438a-45f1-bf96-c5bbe7d4e71b"
        },
        {
          id: "1c637768-2f0b-48e3-9bc0-64c60936b4fe",
          direction: "right",
          type: "image",
          content: "https://pub-d00f0faa09e4457e89f145c79e27b6c9.r2.dev/message-images/1730129878221-pwi39fl.jpeg",
          soundEffect: "",
          ttsURL: "",
          conversationId: "b45389f4-438a-45f1-bf96-c5bbe7d4e71b"
        },
        {
          id: "e0608130-290f-43eb-bc74-cecd57154836",
          direction: "left",
          type: "text",
          content: "yep",
          soundEffect: "",
          ttsURL: "https://pub-d00f0faa09e4457e89f145c79e27b6c9.r2.dev/speeches/1730223670227-IKne3meq5aSn9XLyUdCD.mp3",
          conversationId: "b45389f4-438a-45f1-bf96-c5bbe7d4e71b"
        }
      ]
    }
  ]
};

const FPS = 60;
const DURATION_IN_FRAMES = 450;

const FakeTextAge = ({ params }: { params: { id: string } }) => {
  const totalFrames = sampleData.conversations[0].messages.length * 90;
  
  return (
    <div>
      <Player
        component={() => <Video data={sampleData} />}
        durationInFrames={totalFrames}
        fps={60}
        compositionWidth={1080}
        compositionHeight={1920}
        style={{
          width: '300px',
          height: '700px',
        }}
        controls
        autoPlay
        loop
      />
    </div>
  );
};

export default FakeTextAge

here is the code for the video:

"use client"
import { AbsoluteFill, Audio, useCurrentFrame, interpolate } from 'remotion';

interface Message {
  id: string;
  direction: 'left' | 'right';
  type: 'text' | 'image';
  content: string;
  soundEffect: string;
  ttsURL: string;
  conversationId: string;
}

interface Conversation {
  id: string;
  templateName: string;
  profilePicture: string;
  unreadMessagesCount: number;
  delay: number;
  borderRadius: number;
  scale: number;
  recieverName: string;
  useShadow: boolean;
  shadowColor: string;
  shadowSize: number;
  projectId: string;
  createdAt: string;
  updatedAt: string;
  messages: Message[];
}

interface ConversationsData {
  conversations: Conversation[];
}

const FRAME_PER_MESSAGE = 90;
const CONTAINER_WIDTH = 400;

const MessageBubble: React.FC<{
  message: Message;
  frameOffset: number;
}> = ({ message, frameOffset }) => {
  const frame = useCurrentFrame();
  const opacity = interpolate(
    frame - frameOffset,
    [0, 15],
    [0, 1],
    { extrapolateLeft: 'clamp', extrapolateRight: 'clamp' }
  );

  return (
    <>
      {frame >= frameOffset && (
        <>
          {message.ttsURL && (
            <Audio src={message.ttsURL} />
          )}
          <div
            style={{
              alignSelf: message.direction === 'right' ? 'flex-end' : 'flex-start',
              maxWidth: '70%',
              margin: '4px 10px',
              opacity,
              transform: `translateY(${interpolate(
                frame - frameOffset,
                [0, 15],
                [20, 0],
                { extrapolateLeft: 'clamp', extrapolateRight: 'clamp' }
              )}px)`,
            }}
          >
            <div
              style={{
                backgroundColor: message.direction === 'right' ? '#0A84FF' : '#2C2C2E',
                color: 'white',
                padding: '12px 16px',
                borderRadius: '20px',
                fontSize: '16px',
                marginBottom: '2px',
                overflow: 'hidden',
              }}
            >
              {message.type === 'image' ? (
                <img 
                  src={message.content} 
                  style={{
                    maxWidth: '200px',
                    maxHeight: '200px',
                    borderRadius: '10px',
                  }}
                  alt="Message content"
                />
              ) : (
                message.content
              )}
            </div>
          </div>
        </>
      )}
    </>
  );
};

const Header: React.FC<{
  conversation: Conversation;
}> = ({ conversation }) => (
  <div
    style={{
      height: '60px',
      backgroundColor: '#1C1C1E',
      display: 'flex',
      alignItems: 'center',
      padding: '0 16px',
      borderBottom: '1px solid #2C2C2E',
    }}
  >
    <div style={{ color: '#0A84FF', fontSize: '28px', marginRight: 'auto' }}>
      ‹
    </div>
    <div
      style={{
        textAlign: 'center',
        display: 'flex',
        alignItems: 'center',
        gap: '8px',
      }}
    >
      {conversation.profilePicture ? (
        <img
          src={conversation.profilePicture}
          style={{
            width: '32px',
            height: '32px',
            borderRadius: '16px',
            objectFit: 'cover',
          }}
          alt={conversation.recieverName}
        />
      ) : (
        <div
          style={{
            width: '32px',
            height: '32px',
            borderRadius: '16px',
            backgroundColor: '#444',
          }}
        />
      )}
      <div style={{ color: 'white', fontSize: '16px', fontWeight: 'bold' }}>
        {conversation.recieverName}
      </div>
    </div>
    <div style={{ color: '#0A84FF', fontSize: '24px', marginLeft: 'auto' }}>
      􀵁
    </div>
  </div>
);

const ConversationContainer: React.FC<{
  conversation: Conversation;
}> = ({ conversation }) => {
  return (
    <AbsoluteFill
      style={{
        display: 'flex',
        alignItems: 'flex-start',
        justifyContent: 'center',
        paddingTop: 100,
      }}
    >
      <div
        style={{
          width: CONTAINER_WIDTH,
          backgroundColor: '#000000',
          borderRadius: `${conversation.borderRadius}px`,
          overflow: 'hidden',
          display: 'flex',
          flexDirection: 'column',
          transform: `scale(${conversation.scale / 100})`,
          ...(conversation.useShadow && {
            boxShadow: `0 0 ${conversation.shadowSize}px ${conversation.shadowColor}`,
          }),
        }}
      >
        <Header conversation={conversation} />
        <div
          style={{
            backgroundColor: '#000000',
            display: 'flex',
            flexDirection: 'column',
            padding: '10px 0',
          }}
        >
          {conversation.messages.map((message, index) => (
            <MessageBubble
              key={message.id}
              message={message}
              frameOffset={index * FRAME_PER_MESSAGE}
            />
          ))}
        </div>
      </div>
    </AbsoluteFill>
  );
};

export const Video: React.FC<{
  data: ConversationsData;
}> = ({ data }) => {
  const currentConversation = data.conversations[0];

  return (
    <AbsoluteFill style={{ backgroundColor: '#6366F1' }}>
      <ConversationContainer conversation={currentConversation} />
    </AbsoluteFill>
  );
};

export default Video;

I expect the message to appear the tts url to play and then the next message to the same , but now only "Hello!" plays, but the "yep" doesn't here is my file structure if needed:

project-root/
├── src/
│   ├── app/
│   │   └── fake-text/
│   │       └── [id]/
│   │           └── page.tsx  // Sets up Player component and sampleData
│   └── remotion/
│       └── fake-text/
│           └── main.tsx  // Contains Video and MessageBubble components

Upvotes: 0

Views: 72

Answers (0)

Related Questions