Reactjs react-bootstrap modal "container" property - javascript

I have modal and want to put/open in container, with modal's native property "container", but as soon as I specify class name of the container element, it shows error TypeError: Cannot use 'in' operator to search for 'current' in config
I created example SandBox
Thank you

I'm not entirely sure if this is what you're aiming for, but here's a bootstrap modal that is contained within a div.
Demo
Code
App.js
import { useEffect, useState, useRef } from "react";
import Config from "./Config";
export default function App() {
// create a container ref
const containerRef = useRef(null);
const [show, setShow] = useState(false);
const [isLoading, setLoading] = useState(true);
const hideModal = () => {
setShow(false);
};
useEffect(() => {
// make sure the DOM node is assigned to the containerRef.current property
if (isLoading && containerRef && containerRef.current) setLoading(false);
}, [isLoading]);
return (
<div className="app">
<div className="container">
<div className="row">
<div className="row-items col-3">
<button onClick={() => setShow(true)}>Show</button>
<button onClick={() => setShow(false)}>Close</button>
<hr />
<button>Info</button>
<button>Tests</button>
</div>
<div ref={containerRef} className="modal-container row-items col-9">
Modal should appear here...
<Config
ref={!isLoading ? containerRef.current : null}
hideModal={hideModal}
show={show}
/>
</div>
</div>
</div>
</div>
);
}
Config.js
import { forwardRef } from "react";
import { Modal } from "react-bootstrap";
/*
Forwards the "containerRef" to the "Modal"
The "Modal" component will then be inserted
within the "modal-container" div
*/
const Config = forwardRef(({ hideModal, show }, ref) => (
<Modal
container={ref}
show={show}
backdrop="static"
keyboard={false}
size="md"
centered
>
<div className="analysis-config-header d-block-header">
<i className="fas fa-info-circle align-middle text-info" />
Before we move on...
</div>
<div className="analysis-config-body d-block-body">Options</div>
<div className="analysis-config-action-buttons d-block-action-buttons">
<hr />
<button className="btn btn-danger btn-sm">Save</button>
<button onClick={hideModal} className="btn btn-secondary btn-sm">
Cancel
</button>
</div>
</Modal>
));
export default Config;
index.js
import ReactDOM from "react-dom";
import App from "./App";
import "bootstrap/dist/css/bootstrap.min.css";
import "./styles.css";
ReactDOM.render(<App />, document.getElementById("root"));
styles.css
html,
body,
#root {
min-height: 100vh;
width: 100%;
margin: 0;
padding: 0;
}
.app {
padding: 20px;
}
/* prevents the modal content from bleeding into the container borders */
.modal-content {
margin: auto 20px;
}
/* allows child elements to be positioned relative to the parent div */
.modal-container {
position: relative;
}
/* positions the grey background relative to the parent div */
.modal-backdrop {
position: relative;
width: 100%;
height: calc(100% - 40px);
}
/* positions the modal within the parent div, but in front of the grey
background */
.modal {
position: absolute;
}
.row-items {
border: 1px solid red;
height: 300px;
padding-top: 5px;
}

Related

Why is my React Webcam screenshot appearing as a black image on the screen?

import "./webcam.css"
import React, { useRef, useState, useCallback } from 'react';
import Webcam from 'react-webcam';
import axios from "axios";
import { Button, ButtonGroup } from "#mui/material"
import { FileUpload, RefreshRounded, CameraAltOutlined } from '#mui/icons-material';
import Navbar from '../Navbar/Navbar';
export default function WebcamSample() {
const videoElement = useRef(null);
const [url, setUrl] = useState("");
const videoConstraints = useState({
width: 450,
height: 500,
facingMode: "mirror"
});
const onUserMedia = (e) => console.log(e);
const capturePhoto = useCallback(async () => {
let stream = videoElement.current.stream;
const tracks = stream.getTracks();
await tracks.forEach(track => track.stop());
const imageSrc = videoElement.current.getScreenshot();
setUrl(imageSrc);
}, [videoElement]);
const refreshCapture = () => {
setUrl(null);
};
const uploadPhoto = () => {
console.log(url);
axios.post("http://localhost:3001/vision", {image: url}).then((res) => {
console.log(res);
});
refreshCapture();
};
return (
<>
<Navbar />
<div id="myDiv">
<div id="camView" >
{!url ? (
<Webcam
audio={false}
ref={videoElement}
mirrored={true}
videoConstraints={videoConstraints}
onUserMedia={onUserMedia}
screenshotFormat="image/png"
style={{borderRadius: '15px',}}
/>
) : (
<img id="screengrab" src={url} alt="Screenshot" style={{borderRadius: '15px',}}/>
)}
</div>
<div className="buttons">
<ButtonGroup variant="contained">
<Button
size="small"
endIcon={<CameraAltOutlined />}
onClick={() => capturePhoto()}
>Capture Image</Button>
<Button
size="small"
endIcon={<RefreshRounded />}
onClick={() => refreshCapture()}
>Refresh</Button>
{url &&
<Button
size="small"
endIcon={<FileUpload />}
onClick={() => uploadPhoto()}
>Upload</Button>
}
</ButtonGroup>
</div>
</div>
</>
);
};
My CSS File Below. My aim was to use a div to create a border around the camera.
#myDiv{
background-image:url("../../Assets/Background.svg");
background-size: cover;
width: 100%;
height: 100vh;
display: flex;
justify-content: center;
align-items: center;
text-align: center;
}
#camView{
min-height: 490px;
max-height: 490px;
background-color: #133275;
min-width:645px;
padding-top: 0.2%;
border-radius: 15px;
margin-bottom: 15%;
position:absolute;
}
.buttons
{
padding-top: 1%;
margin-top:15%;
position:absolute;
}
My buttons are moving when I change window size but I would also like them to stay in the same spot.
The Webcam Screenshot was showing before but now it is only showing a black screen. Ideally once the user presses the "Capture Image" button the react webcam takes a screenshot of the current image on the camera and displays it over it. This functionality is technically working except the image showing is black.

How to have dimmed content on Semantic UI React (NextJS)

Im having a problem on implementing dimmed content on semantic ui react sidebar on nextjs...
This is the dimmed content on semantic ui
https://react.semantic-ui.com/modules/sidebar/#states-dimmed
this is my layout code:
import React, { useState } from 'react';
import CartSidebar from './CartSidebar';
import Navbar from './Navbar';
const StoreLayout = ({ children }) => {
const [toggleCart, setToggleCart] = useState(false);
function toggleMenuCart() {
setToggleCart(!toggleCart);
}
return (
<>
<CartSidebar toggleMenu={toggleCart} />
<Navbar onToggleMenuCart={toggleMenuCart} />
{children}
</>
);
};
export default StoreLayout;
this is my navbar code:
<nav>
<div className="borderLeftList">
<li className="cart">
<Button
onClick={props.onToggleMenuCart}
className="cart-icon empty"
/>
</li>
</div>
</nav>
this is my sidebar code:
import React, { useState } from 'react';
import cn from 'classnames';
import { Icon, Menu } from 'semantic-ui-react';
import Link from 'next/link';
export default function CartSidebar(props) {
const classes = cn(
'ui',
'sidebar',
'push',
'right',
'inverted',
'menu',
'vertical',
'animating',
{ visible: props.toggleMenu }
);
return (
<div className={classes}>
<Menu.Item as={Link} href="/admin">
<a>
<i className="fa fa-home" />
Dashboard
</a>
</Menu.Item>
<Menu.Item as={Link} href="/admin/orders">
Second Menu
</Menu.Item>
<Menu.Item as={Link} href="/admin/products">
Third Menu
</Menu.Item>
</div>
);
}
this is my _app.js code:
<StoreLayout>
<Component {...pageProps} />
</StoreLayout>
if you need any more details you can ask on the comment... Thank you so much in advance!!! :)
The documentation shows it will dim all of its children:
<Dimmer active={true} page>
<ChildComponent/>
</Dimmer>
Which will then dim the child component. Along with that you can also specify properties like "page" to tell it to dim the whole page.
If you're trying to use it with sidebar, then you have to wrap the content for sidebar in a dimmer.
const Page = () => {
const [active, setActive] = useState(false)
return <div>
<Sidebar setActive={setActive}/>
<Dimmer active={active} page> // this is a child
<Content/>
</Dimmer>
</div>
}
Then in the sidebar you'll have to set the active when you click an item or whatever. This example isn't perfect, just gives you a rough idea of what you can do.
Alternatively:
.dimmed {
background: black;
opacity: 0.5;
}
You can also just do it yourself and apply a class with opacity to whatever needs to be dimmed.
CREDITS ON #Matriarx for giving me idea on how to answer his question...
You have to import the Dimmer on sematic-ui-react and then parent the child using this code:
<Dimmer.Dimmable dimmed={toggleCart}>
<Dimmer
className="dimmedContent"
active={toggleCart}
onClickOutside={handleHide}
/>
put this on your css so that you can give yourself a style, without this css you cant make the dimmed fullscreen
.dimmedContent {
display: block !important;
position: fixed !important;
top: 0 !important;
left: 0 !important;
right: 0 !important;
bottom: 0 !important;
background: rgba(0, 0, 0, 0.25) !important;
cursor: default !important;
z-index: 8 !important;
}
this is the full code:
import React, { useState } from 'react';
import { Dimmer } from 'semantic-ui-react';
import CartSidebar from './CartSidebar';
import Navbar from './Navbar';
const StoreLayout = ({ children }) => {
const [toggleCart, setToggleCart] = useState(false);
function toggleMenuCart() {
setToggleCart(!toggleCart);
}
const handleHide = () => {
setToggleCart({ active: false });
};
return (
<>
<Dimmer.Dimmable dimmed={toggleCart}>
<Dimmer
className="dimmedContent"
active={toggleCart}
onClickOutside={handleHide}
/>
<CartSidebar toggleMenu={toggleCart} />
<Navbar onToggleMenuCart={toggleMenuCart} />
{children}
</Dimmer.Dimmable>
</>
);
};
export default StoreLayout;
also dont forget to put the css that i provided above :)
Cheers!

In React, styled component's flex not working

I trying to work with styled-components. However now, I 'm using "flex" for responsive design, But I can't figure it out.
CSS of styled-components doesn't work. I don't see those styles on my website
Below is outline of my styling
import TagsInput from 'react-tagsinput';
import PostTypeSelector from './PostTypeSelector';
import styled from 'styled-components';
import PostMarkdown from './PostMarkdown';
import PostSubmit from './PostSubmit';
// const StyledPostSubmit = styled(PostSubmit)`
// `;
// const StyledTagsInput = styled(TagsInput)`
// `;
const StyledPostTypeSelector = styled(PostTypeSelector)`
background-color: gray;
flex: 1 0;
`;
const StyledPostForm = styled(PostForm)`
flex: 9 0;
`;
const StyledPostMarkdown = styled(PostMarkdown)`
flex: 10 0;
border-left: 1px solid #222222;
`;
and I adjust like this
render() {
return (
<div className="posting">
<div className="plain-post-form-0">
<div className="plain-post-form-1">
<div style={{
display: 'flex',
flexDirection:'row',
width: '800px'
}}
className="plain-post-form-2"
>
<StyledPostForm
onSave={this.handleSave}
post={this.initValue()}
/>
<StyledPostTypeSelector
/>
<StyledPostMarkdown
post={this.state}
/>
</div>
<TagsInput
value={this.state.tags}
onChange={this.handleTagsChange}
/>
<PostSubmit
data={this.handleCommit}
target={post}
method="post"
value="Commit"
/>
</div>
</div>
</div>
);
}
As stated in the docs:
If you use the styled(MyComponent) notation and MyComponent does not render the passed-in className prop, then no styles will be applied.
// For this to work
const StyledPostForm = styled(PostForm)`
flex: 9 0;
`;
// You need to apply the className prop to component's top node (Container/Parent)
const PostForm = ({ className }) => (
<Container className={className}>...</Container>
)

Custom Accordion Component not rendering body elements

I have a collapse/accordion component from Antd that I customized and exported from an elements folder from within my application so that I could reuse it across the app.
When I import it and include it inside another component I can't render any of the body elements inside. Does anyone have any idea why this is happening and if there's a way around it?
Also as a smaller side issue when the body of the accordion opens to display, the whitespace doesn't fill the entire container and it looks like there's a grey column running down the right side.
I've included a code sandbox here to better show what I mean
Custom Collapse Component
import React, { useState } from "react";
import styled from "styled-components";
import { Collapse as AntCollapse } from "antd";
const StyledCollapse = styled(AntCollapse)`
&&& {
border: none;
border-radius: 0px;
background-color: #f7f7f7;
box-shadow: none;
}
`;
const CustomCollapse = props => {
const [disabled, setDisabled] = useState(true);
return (
<StyledCollapse onChange={() => setDisabled(prev => !prev)}>
<AntCollapse.Panel
header={props.header}
key="1"
showArrow={false}
bordered={false}
extra={<p style={{ color: "#0076de" }}>{disabled ? "SHOW" : "HIDE"}</p>}
/>
</StyledCollapse>
);
};
export default CustomCollapse;
Main Component
import React from "react";
import ReactDOM from "react-dom";
import styled from "styled-components";
import "antd/dist/antd.css";
import AntCollapse from "./CustomCollapse";
const Flexbox = styled.div`
font-family: sans-serif;
flex-direction: column;
display: flex;
justify-content: center;
border: solid 1px palevioletred;
padding: 10%;
margin: 10%;
`;
const ConfigurationOptions = () => (
<Flexbox>
<AntCollapse header="configuration test">
<h1>Test</h1>
<p>Test Paragraph</p>
<p>Test Paragraph</p>
</AntCollapse>
</Flexbox>
);
const rootElement = document.getElementById("root");
ReactDOM.render(<ConfigurationOptions />, rootElement);
You forgot to pass down the children in your custom collapse component.
To get it to work, do this:
const CustomCollapse = props => {
const [disabled, setDisabled] = useState(true);
return (
<StyledCollapse onChange={() => setDisabled(prev => !prev)}>
<AntCollapse.Panel
header={props.header}
key="1"
showArrow={false}
bordered={false}
extra={<p style={{ color: "#0076de" }}>{disabled ? "SHOW" : "HIDE"}</p>}
>
{props.children}
</AntCollapse.Panel>
</StyledCollapse>
);
};
(also to get the weird grey side column off the side you should do it like this:
const CustomCollapse = props => {
const [disabled, setDisabled] = useState(true);
return (
<StyledCollapse onChange={() => setDisabled(prev => !prev)}>
<AntCollapse.Panel
header={
<span>
{props.header}
<span style={{ color: "#0076de", float: "right" }}>
{disabled ? "SHOW" : "HIDE"}
</span>
</span>
}
key="1"
showArrow={false}
bordered={false}
>
{props.children}
</AntCollapse.Panel>
</StyledCollapse>
);
};
)

how to set duration for transition for styled-components in React

I am trying to create my own slider in React, and I'm having problems with the transition duration. I cannot set it.
This is what I've tried so far.
import React, { Component } from "react";
import Slide from "./Slide";
import slide0 from "../../assets/images/sky.jpg";
import slide1 from "../../assets/images/3monkeys.jpg";
import slide2 from "../../assets/images/tree.jpg";
import slide3 from "../../assets/images/moon.jpg";
import slide4 from "../../assets/images/woman.jpg";
import slide5 from "../../assets/images/railways.jpg";
import classes from "./Slider.scss";
import styled from "styled-components";
class Slider extends Component {
state = {
position: -26
};
narrowRight() {
this.setState({
position: this.state.position - 13
});
}
narrowLeft() {
this.setState({ position: this.state.position + 13 });
}
render() {
const Wrapper = styled.div`
width: 100%;
height: 100%;
display: flex;
overflow: hidden;
`;
const Slidest = styled.div`
display: flex;
transition: transform 1s ease;
transform: translateX(${this.state.position}%);
`;
return (
<div>
<Wrapper>
<Slidest className={classes.Slider}>
<Slide source={slide0} alt={"sky"} />
<Slide source={slide1} alt={"s"} />
<Slide source={slide2} alt={"sk"} />
<Slide source={slide3} alt={"skys"} />
<Slide source={slide4} alt={"skyss"} />
<Slide source={slide5} alt={"skysss"} />
</Slidest>
</Wrapper>
<div className={classes.Slider}>
<i
onClick={() => this.narrowLeft()}
className="fas fa-5x fa-chevron-circle-left"
/>
<i
onClick={() => this.narrowRight()}
className="fas fa-5x fa-chevron-circle-right"
/>
</div>
</div>
);
}
}
export default Slider;

Categories