Looking to showcase API images in a three-column layout?

I have a challenge with displaying images fetched from an API in the browser. I intended to show them beautifully in 3 columns, but after implementing react semantic UI's Grid and react-bootstrap's CardColumns, they all appear in just one column. https://i.sstatic.net/IYMVD.png

import React, { useEffect } from 'react';
import PropTypes from 'prop-types';
import { Link } from 'react-router-dom';
import { useSelector, useDispatch } from 'react-redux';
import { Grid, Container } from 'semantic-ui-react';
import Button from 'react-bootstrap/Button';
import { CardColumns } from 'react-bootstrap';
import Card from 'react-bootstrap/Card';
import { fetchMealsStartAsync } from '../actions/getMeals';

const MealList = (props) => {
  const { cat } = props;
  const meals = useSelector((state) => state.meals.meals);

  const dispatch = useDispatch();

  useEffect(() => {
    dispatch(fetchMealsStartAsync(cat));
  }, [cat]);

  return (
    <Container textalign="center" style={{ marginTop: 40 }}>
      <Grid>
        <Grid.Row>
          {
            meals && meals.map((meal) => (
              <CardColumns
                key={meal.strMeal}
                style={{ marginTop: 20 }}
                as={Link}
                to={{
                  pathname: `/ingredients/${meal.idMeal}`,
                  id: meal.idMeal,
                }}
              >
                <Card className="m-2 pb-1" style={{ width: '18rem' }}>
                  <Card.Img variant="top" src={meal.strMealThumb} />
                  <Card.Body>
                    <Card.Title>
                      {meal.strMeal}
                    </Card.Title>
                    <Button variant="primary">
                      Get Recipe
                    </Button>
                  </Card.Body>
                </Card>
              </CardColumns>
            ))
          }
        </Grid.Row>
      </Grid>
    </Container>
  );
};

MealList.propTypes = {
  cat: PropTypes.string,
};

MealList.defaultProps = {
  cat: '',
};

export default MealList;

Answer №1

Consider this approach: gather your three, or even more items that you have retrieved and place them within a main container div. Then, apply the CSS selector to the parent div like so:

display: flex; flex-direction: row;

Answer №2

After modifying the code snippet from <Grid.Row> to <Grid.Column>, I included Bootstrap styling by updating it to:

<Grid.Column className="d-flex flex-wrap">
https://i.sstatic.net/0snt3.jpg

Answer №3

If you want to create a 3-column layout in a browser display, you can achieve it by using the following code:

<Grid columns={3}>
      <Grid.Column>
        <Segment>Content</Segment>
      </Grid.Column>
      <Grid.Column>
        <Segment>Content</Segment>
      </Grid.Column>
      <Grid.Column>
        <Segment>Content</Segment>
      </Grid.Column>
</Grid>

You can also replace the entire code snippet with this modified version:

import React, { useEffect } from 'react';
import PropTypes from 'prop-types';
import { Link } from 'react-router-dom';
import { useSelector, useDispatch } from 'react-redux';
import { Grid, Container } from 'semantic-ui-react';
import Button from 'react-bootstrap/Button';
import { CardColumns } from 'react-bootstrap';
import Card from 'react-bootstrap/Card';
import { fetchMealsStartAsync } from '../actions/getMeals';

const MealList = (props) => {
  const { cat } = props;
  const meals = useSelector((state) => state.meals.meals);

  const dispatch = useDispatch();

  useEffect(() => {
    dispatch(fetchMealsStartAsync(cat));
  }, [cat]);

  return (
    <Container textalign="center" style={{ marginTop: 40 }}>
      <Grid>
        <Grid.Row columns={3}>
          {
            meals && meals.map((meal) => (
             <Grid.Column>
              <CardColumns
                key={meal.strMeal}
                style={{ marginTop: 20 }}
                as={Link}
                to={{
                  pathname: `/ingredients/${meal.idMeal}`,
                  id: meal.idMeal,
                }}
              >
                <Card className="m-2 pb-1" style={{ width: '18rem' }}>
                  <Card.Img variant="top" src={meal.strMealThumb} />
                  <Card.Body>
                    <Card.Title>
                      {meal.strMeal}
                    </Card.Title>
                    <Button variant="primary">
                      Get Recipe
                    </Button>
                  </Card.Body>
                </Card>
              </CardColumns>
              </Grid.Column>
            ))
          }
        </Grid.Row>
      </Grid>
    </Container>
  );
};

MealList.propTypes = {
  cat: PropTypes.string,
};

MealList.defaultProps = {
  cat: '',
};

export default MealList;

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Enhance the security of Laravel 5.4 by restricting guest access to API routes connecting the front end and back end

I'm currently developing a new application that utilizes AngularJS for the front end and Laravel as a RESTful back end. The app retrieves data from the API for guest users visiting the site. I'm exploring options to secure the API routes from dir ...

Dynamic classroom experience featuring a bootstrap sidebar

I am having an issue with changing the active class of the sidebar after a click event. I have tried using Bootstrap and implemented some JavaScript code, but it doesn't seem to be working properly. $(function(){ $('.sidebar1 a').filt ...

Can you provide me with instructions on how to utilize the data-testid attribute in a React Component Test?

I am currently conducting a Component Test on a basic react component, aiming to render it and perform some testing activities. However, I am facing an issue where cy.get() is unable to locate the component using a data-testid attribute. To confirm this b ...

What is the best way to ensure the second navbar stays at the top when scrolling, after the first one?

Looking for a solution to create a navbar with two distinct sections for contact info and the menu. The goal is to have the contact info disappear when scrolling down, while the menu remains fixed at the top of the page. When scrolling back up, the menu sh ...

Issue with Material-UI CardContent not displaying correctly with extra breaks

One issue I encountered involves a component that renders a Material-UI Card. It takes in a string, such as: 'This is a test' Despite the input being on multiple lines, it displays as 'This is a test' all on one line. I attempted solut ...

Tips for eliminating the default margin without using a float

Exploring the world of divs and buttons led me to an interesting discovery: removing a float creates a natural margin. Upon entering this styling: body { background: gray; } button { font-size: 17px; color: white; margin-l ...

Styling for the DataTable disappears upon loading jQuery

my PHP file named "zero3data.php" <?php printf('<table cellpadding="0" cellspacing="0" border="0" class="display" id="example" width="100%">'); printf('<thead>'); printf('<tr>'); ...

React is displaying [object Object] instead of the intended value on the webpage. What steps can be taken to resolve this issue?

I have attempted to retrieve data from an API and am currently working on displaying this data within a table cell inside a component. Instead of rendering the original data, React is displaying [object Object]. I tried using the join() method with commas ...

IE9 Z-index Issue

Currently, I am facing an issue with two images not displaying correctly on a website that I am working on. The problem seems to be specific to IE 9, as other browsers are working fine. The trouble arises when I try to create a slideshow with a shadow back ...

The best approach for setting a select value and managing state in React using TypeScript

Currently, I am in the process of familiarizing myself with TypeScript within my React projects. I have defined a type for the expected data structure (consisting of name and url). type PokedexType = { name: string; url: string; } The API respon ...

Sync JSON object modifications with the DOM using jQuery (or potentially other libraries)

I am working on developing a web application that would be able to update the HTML elements based on changes in a JSON object. For instance, I have an unordered list with data attributes: <ul data-id="elements"> <li data-id="01">Element 01< ...

What steps should I take in order to modify the color of my header background?

I'm facing an issue with changing the background color of the header along the navigation menu using HTML/CSS. It seems that my current code is not working as expected. I believe that the header selector should contain my topnav section, but changing ...

What is the best method for properly inserting images into a Vue Carousel 3D slider?

I'm currently exploring the Vue Carousel 3D documentation and I am having trouble displaying a single image on each slide. Let me elaborate: I aim to create a slider similar to the one shown in the Controls Customized example in the documentation. Th ...

Property finally is missing in the Response type declaration, making it unassignable to type Promise<any>

After removing the async function, I encountered an error stating that the Promise property finally is missing when changing from an async function to a regular function. Any thoughts on why this would happen? handler.ts export class AccountBalanceHandle ...

React: The received value for the prop type must be a function, but it was an object

I'm stuck trying to make sense of this error message, and my online search has hit a dead end. Any insights would be greatly appreciated! Attention: Prop type validation failed - expected prop type `leoInfo` to be a function from the `prop-types` pack ...

What causes the image to vanish once the CSS animation is activated?

Is there a reason why the image disappears after the animation completes? :/ .coin { width: 200px; height: 200px; background-size: cover; animation: CoinflipRoll 6s steps(199); animation-delay: .5s; animation-fill-mode: forwards; ...

Place a div element on top of the others by using the onClick() event to "dock" it

Can someone help me with setting/docking a div element above another div? The div contains some other divs and form objects, serving as an inputbox dialog that should appear right above an element when clicked. I have set the onClick() event for a Click &l ...

Sliding Tab Animation using solely CSS on Flexbox

I've been challenged with developing my own React Tabs component that includes a sliding animation, similar to what you see in mui or ant design. I can achieve this using JavaScript, however, the limitation is that I cannot use CSS within JavaScript ...

Programmatically setting the active tab in a Tab component from Material UI

I am currently working on a project using Material UI and React. As part of the functionality, I am programmatically creating multiple tabs, as shown in the code snippet below: return ( <div> <Tabs> {this.state.elements ...

Firefox truncates content when printing HTML pages

Having an issue with printing an HTML page in Firefox where the page is cut off, even though it works fine in IE9 and Chrome. See below for the HTML code snippet: <!DOCTYPE html> <html lang="de"> <head> <meta http-equiv="Content- ...