olefrank
olefrank

Reputation: 6820

import mp3 file in CRA / TypeScript

I have a simple app built in CRA v3.2.0. I use TypeScript with the default settings (see tsconfig.ts below). In /src/sounds/ I have a mp3 file "click_hi.mp3" that I want to use in a component, but I can't import the mp3 with the error Cannot find module 'sounds/click_hi.mp3'.ts(2307).

I tried putting the file in the same folder as the component to be sure to avoid typos in the path. But no luck... How can I import the mp3 file?

App.tsx

import React, { useState, useRef, useEffect } from "react";
import ReactDOM from "react-dom";
import { Sampler } from "tone";
import ClickHi from 'sounds/click_hi.mp3'


export default function ExercisePage() {
  const [isLoaded, setLoaded] = useState(false);
  const sampler = useRef(null);

  useEffect(() => {
    sampler.current = new Sampler(
      { "A1": ClickHi },
      {
        onload: () => {
          setLoaded(true);
        }
      }
    ).toMaster();
  }, []);

  const handleClick = () => sampler.current.triggerAttack("A1");

  return (
    <div>
      <button disabled={!isLoaded} onClick={handleClick}>
        start
      </button>
    </div>
  );
}

tsconfig.ts

{
  "compilerOptions": {
    "baseUrl": "src",
    "target": "es5",
    "lib": ["dom", "dom.iterable", "esnext"],
    "allowJs": true,
    "skipLibCheck": true,
    "esModuleInterop": true,
    "allowSyntheticDefaultImports": true,
    "strict": true,
    "forceConsistentCasingInFileNames": true,
    "module": "esnext",
    "moduleResolution": "node",
    "resolveJsonModule": true,
    "isolatedModules": true,
    "noEmit": true,
    "jsx": "react"
  },
  "include": ["src"]
}

Upvotes: 2

Views: 4340

Answers (2)

Geocarlos
Geocarlos

Reputation: 136

For anybody still having this issue, and just like me, does not want to place the assets in the public folder, do it like this, using "default":

const path = require('../assets/audio/some_audio.mp3');
setAudio(new Audio(path.default));

Note: I only have had this problem using TypeScript. You need to declare a module for mp3, by adding to your project src folder a file named something like "audio.d.ts" and content like declare module '.*mp3';

Example of simple app working, using this: https://geocarlos.github.io/leiamos/

Upvotes: 5

olefrank
olefrank

Reputation: 6820

I fixed it by placing the audio file in the public folder and referencing it like this:

useEffect(() => {
    sampler.current = new Sampler(
      { A1: `${process.env.PUBLIC_URL}/audio/click_hi.mp3`},
      () => {
          setLoaded(true);
      }
    ).toMaster();
  }, []);

Upvotes: 2

Related Questions