So for Dustbin.jsx you will need to create an object of images with key-value as name of the image and the source. Then, appending backgroundImage while passing the style object to the div. Now, when you create a Dustbin component, just pass the name of the image you want to render as a prop (I called it bgImageName). Like this:
Dustbin.jsx
import React from "react";
import { DropTarget } from "react-dnd";
// THIS IS THE IMAGES LIST
const backgroundsList = {
tree:
"https://cdn.pixabay.com/photo/2020/02/17/19/33/tree-4857597_960_720.png",
avocado:
"https://cdn.pixabay.com/photo/2020/05/04/18/55/avocado-5130214_960_720.png",
snowman:
"https://cdn.pixabay.com/photo/2019/12/22/01/14/snowman-4711637_960_720.png"
};
const style = {
height: "12rem",
width: "12rem",
marginRight: "1.5rem",
marginBottom: "1.5rem",
color: "white",
padding: "1rem",
textAlign: "center",
fontSize: "1rem",
lineHeight: "normal",
float: "left",
backgroundSize: "contain" // TO FIT DIV
};
export const Dustbin = ({
accepts,
isOver,
canDrop,
connectDropTarget,
lastDroppedItem,
bgImageName
}) => {
const isActive = isOver && canDrop;
let backgroundColor = "#222";
if (isActive) {
backgroundColor = "darkgreen";
} else if (canDrop) {
backgroundColor = "darkkhaki";
}
let backgroundImage = `url(${backgroundsList[bgImageName]})`; // PASS A PROPERTY CALLED bgImageName WITH THE NAME OF THE IMAGE WE WANT.
return connectDropTarget(
<div style={{ ...style, backgroundColor, backgroundImage }}> // APPEND HERE
{isActive
? "Release to drop"
: `This dustbin accepts: ${accepts.join(", ")}`}
{lastDroppedItem && (
<p>Last dropped: {JSON.stringify(lastDroppedItem)}</p>
)}
</div>
);
};
export default DropTarget(
(props) => props.accepts,
{
drop(props, monitor) {
props.onDrop(monitor.getItem());
}
},
(connect, monitor) => ({
connectDropTarget: connect.dropTarget(),
isOver: monitor.isOver(),
canDrop: monitor.canDrop()
})
)(Dustbin);
And in Container.jsx add a property of background image to each dustbin object, and pass it to the component. like this:
Container.jsx
import React, { useState, useCallback } from "react";
import { NativeTypes } from "react-dnd-html5-backend";
import Dustbin from "./Dustbin";
import Box from "./Box";
import { ItemTypes } from "./ItemTypes";
import update from "immutability-helper";
export const Container = () => {
// ADD bgImageName TO EACH DUSTBIN OBJECT
const [dustbins, setDustbins] = useState([
{ accepts: [ItemTypes.GLASS], lastDroppedItem: null, bgImageName: "tree" },
{
accepts: [ItemTypes.FOOD],
lastDroppedItem: null,
bgImageName: "avocado"
},
{
accepts: [ItemTypes.PAPER, ItemTypes.GLASS, NativeTypes.URL],
lastDroppedItem: null,
bgImageName: "snowman"
},
{
accepts: [ItemTypes.PAPER, NativeTypes.FILE],
lastDroppedItem: null,
bgImageName: "tree"
}
]);
const [boxes] = useState([
{ name: "Bottle", type: ItemTypes.GLASS },
{ name: "Banana", type: ItemTypes.FOOD },
{ name: "Magazine", type: ItemTypes.PAPER }
]);
const [droppedBoxNames, setDroppedBoxNames] = useState([]);
function isDropped(boxName) {
return droppedBoxNames.indexOf(boxName) > -1;
}
const handleDrop = useCallback(
(index, item) => {
const { name } = item;
setDroppedBoxNames(
update(droppedBoxNames, name ? { $push: [name] } : { $push: [] })
);
setDustbins(
update(dustbins, {
[index]: {
lastDroppedItem: {
$set: item
}
}
})
);
},
[droppedBoxNames, dustbins]
);
return (
<div>
<div style={{ overflow: "hidden", clear: "both" }}>
{dustbins.map(({ accepts, lastDroppedItem, bgImageName }, index) => (
<Dustbin
accepts={accepts}
lastDroppedItem={lastDroppedItem}
onDrop={(item) => handleDrop(index, item)}
key={index}
bgImageName={bgImageName} // DONT FORGET TO PASS bgImageName PROPERTY TO Dustbin COMPONENT
/>
))}
</div>
<div style={{ overflow: "hidden", clear: "both" }}>
{boxes.map(({ name, type }, index) => (
<Box
name={name}
type={type}
isDropped={isDropped(name)}
key={index}
/>
))}
</div>
</div>
);
};
Codesandbox here