Legal privacy

This commit is contained in:
Janis Meister
2023-03-10 10:22:15 +01:00
parent 1fd417d6c3
commit 3cf6a62477
12 changed files with 1270 additions and 405 deletions

63
package-lock.json generated
View File

@@ -9,7 +9,8 @@
"version": "0.0.0", "version": "0.0.0",
"dependencies": { "dependencies": {
"react": "^18.2.0", "react": "^18.2.0",
"react-dom": "^18.2.0" "react-dom": "^18.2.0",
"react-router-dom": "^6.8.2"
}, },
"devDependencies": { "devDependencies": {
"@types/node": "^18.14.6", "@types/node": "^18.14.6",
@@ -373,6 +374,14 @@
"node": ">=12" "node": ">=12"
} }
}, },
"node_modules/@remix-run/router": {
"version": "1.3.3",
"resolved": "https://registry.npmjs.org/@remix-run/router/-/router-1.3.3.tgz",
"integrity": "sha512-YRHie1yQEj0kqqCTCJEfHqYSSNlZQ696QJG+MMiW4mxSl9I0ojz/eRhJS4fs88Z5i6D1SmoF9d3K99/QOhI8/w==",
"engines": {
"node": ">=14"
}
},
"node_modules/@swc/core": { "node_modules/@swc/core": {
"version": "1.3.38", "version": "1.3.38",
"resolved": "https://registry.npmjs.org/@swc/core/-/core-1.3.38.tgz", "resolved": "https://registry.npmjs.org/@swc/core/-/core-1.3.38.tgz",
@@ -937,6 +946,36 @@
"react": "^18.2.0" "react": "^18.2.0"
} }
}, },
"node_modules/react-router": {
"version": "6.8.2",
"resolved": "https://registry.npmjs.org/react-router/-/react-router-6.8.2.tgz",
"integrity": "sha512-lF7S0UmXI5Pd8bmHvMdPKI4u4S5McxmHnzJhrYi9ZQ6wE+DA8JN5BzVC5EEBuduWWDaiJ8u6YhVOCmThBli+rw==",
"dependencies": {
"@remix-run/router": "1.3.3"
},
"engines": {
"node": ">=14"
},
"peerDependencies": {
"react": ">=16.8"
}
},
"node_modules/react-router-dom": {
"version": "6.8.2",
"resolved": "https://registry.npmjs.org/react-router-dom/-/react-router-dom-6.8.2.tgz",
"integrity": "sha512-N/oAF1Shd7g4tWy+75IIufCGsHBqT74tnzHQhbiUTYILYF0Blk65cg+HPZqwC+6SqEyx033nKqU7by38v3lBZg==",
"dependencies": {
"@remix-run/router": "1.3.3",
"react-router": "6.8.2"
},
"engines": {
"node": ">=14"
},
"peerDependencies": {
"react": ">=16.8",
"react-dom": ">=16.8"
}
},
"node_modules/readdirp": { "node_modules/readdirp": {
"version": "3.6.0", "version": "3.6.0",
"resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz",
@@ -1258,6 +1297,11 @@
"dev": true, "dev": true,
"optional": true "optional": true
}, },
"@remix-run/router": {
"version": "1.3.3",
"resolved": "https://registry.npmjs.org/@remix-run/router/-/router-1.3.3.tgz",
"integrity": "sha512-YRHie1yQEj0kqqCTCJEfHqYSSNlZQ696QJG+MMiW4mxSl9I0ojz/eRhJS4fs88Z5i6D1SmoF9d3K99/QOhI8/w=="
},
"@swc/core": { "@swc/core": {
"version": "1.3.38", "version": "1.3.38",
"resolved": "https://registry.npmjs.org/@swc/core/-/core-1.3.38.tgz", "resolved": "https://registry.npmjs.org/@swc/core/-/core-1.3.38.tgz",
@@ -1626,6 +1670,23 @@
"scheduler": "^0.23.0" "scheduler": "^0.23.0"
} }
}, },
"react-router": {
"version": "6.8.2",
"resolved": "https://registry.npmjs.org/react-router/-/react-router-6.8.2.tgz",
"integrity": "sha512-lF7S0UmXI5Pd8bmHvMdPKI4u4S5McxmHnzJhrYi9ZQ6wE+DA8JN5BzVC5EEBuduWWDaiJ8u6YhVOCmThBli+rw==",
"requires": {
"@remix-run/router": "1.3.3"
}
},
"react-router-dom": {
"version": "6.8.2",
"resolved": "https://registry.npmjs.org/react-router-dom/-/react-router-dom-6.8.2.tgz",
"integrity": "sha512-N/oAF1Shd7g4tWy+75IIufCGsHBqT74tnzHQhbiUTYILYF0Blk65cg+HPZqwC+6SqEyx033nKqU7by38v3lBZg==",
"requires": {
"@remix-run/router": "1.3.3",
"react-router": "6.8.2"
}
},
"readdirp": { "readdirp": {
"version": "3.6.0", "version": "3.6.0",
"resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz",

View File

@@ -10,7 +10,8 @@
}, },
"dependencies": { "dependencies": {
"react": "^18.2.0", "react": "^18.2.0",
"react-dom": "^18.2.0" "react-dom": "^18.2.0",
"react-router-dom": "^6.8.2"
}, },
"devDependencies": { "devDependencies": {
"@types/node": "^18.14.6", "@types/node": "^18.14.6",

View File

@@ -1,185 +1,25 @@
import { ChangeEvent, useEffect, useRef, useState } from "react"; import React from "react";
import "@/assets/styles/app.scss"; import Generator from "./Generator";
import { generatePassword } from "./generator";
import Footer from "./Footer"; import Footer from "./Footer";
import { BrowserRouter, Routes, Route } from "react-router-dom";
const colorWeak = "#eb130c"; import "@/assets/styles/app.scss";
const colorGood = "#31f399 "; import Legal from "./Legal";
const colorBest = "#1fff3d"; import Privacy from "./Privacy";
function App() { function App() {
const [password, setPassword] = useState("");
const [length, setLength] = useState(64);
const [numbers, setNumbers] = useState(true);
const [symbols, setSymbols] = useState(true);
const [uppercase, setUppercase] = useState(true);
const [lowercase, setLowercase] = useState(true);
const [similar, setSimilar] = useState(false);
const [ambiguous, setAmbiguous] = useState(false);
const copiedTooltipRef = useRef<HTMLDivElement>(null);
const lengthCounterRef = useRef<HTMLInputElement>(null);
function copy() {
navigator.clipboard.writeText(password);
if (copiedTooltipRef.current) {
copiedTooltipRef.current.style.animation = "tooltipAnimation 200ms";
copiedTooltipRef.current.style.opacity = "1";
setTimeout(() => {
if (copiedTooltipRef.current) {
copiedTooltipRef.current.style.opacity = "0";
copiedTooltipRef.current.style.animation = "";
}
}, 1000);
}
}
function generate() {
setPassword(
generatePassword({
length: length,
numbers: numbers,
symbols: symbols,
uppercase: uppercase,
lowercase: lowercase,
excludeSimilar: similar,
excludeAmbiguous: ambiguous,
})
);
}
useEffect(() => {
generate();
}, []);
useEffect(() => {
if (lengthCounterRef.current) {
if (length >= 8 && length <= 16) {
lengthCounterRef.current.style.borderColor = colorWeak;
} else if (length > 16 && length <= 256) {
lengthCounterRef.current.style.borderColor = colorGood;
} else if (length > 256 && length <= 2048) {
lengthCounterRef.current.style.borderColor = colorBest;
}
}
}, [length]);
return ( return (
<div className="app"> <div className="app">
<div id="headline"> <BrowserRouter>
<h1>SecureKeyGen</h1> <Routes>
<h3>Generate secure passwords</h3> <Route path="/">
</div> <Route index element={<Generator />} />
<div id="content"> <Route path="legal" element={<Legal />} />
<div id="result"> <Route path="privacy" element={<Privacy />} />
<p id="password"> <Route path="*" element={<Generator />} />
<code>{password}</code> </Route>
</p> </Routes>
<button onClick={copy} id="copy"> </BrowserRouter>
Copy
</button>
<div ref={copiedTooltipRef} id="copiedTooltip">
Copied!
</div>
</div>
<button onClick={generate}>Generate</button>
<div id="length">
<label>Length</label>
<input
onChange={(e: ChangeEvent<HTMLInputElement>) => {
// setLength but clamp it between 8 and 2048
setLength(Math.min(2048, Math.max(8, parseInt(e.target.value))));
}}
type="range"
min="8"
max="2048"
value={length}
/>
<input
type="number"
ref={lengthCounterRef}
onInput={(e: ChangeEvent<HTMLInputElement>) => {
// setLength but clamp it between 8 and 2048
setLength(Math.min(2048, Math.max(8, parseInt(e.target.value))));
}}
value={length}
max={2048}
min={8}
/>
</div>
<div id="checkboxes">
<div>
<div className="checkboxContainer">
<input
type="checkbox"
checked={uppercase}
onChange={(e: ChangeEvent<HTMLInputElement>) => {
setUppercase(e.target.checked);
}}
/>
<label>Include uppercase</label>
</div>
<div className="checkboxContainer">
<input
type="checkbox"
checked={lowercase}
onChange={(e: ChangeEvent<HTMLInputElement>) => {
setLowercase(e.target.checked);
}}
/>
<label>Include lowercase</label>
</div>
<div className="checkboxContainer">
<input
type="checkbox"
checked={numbers}
onChange={(e: ChangeEvent<HTMLInputElement>) => {
setNumbers(e.target.checked);
}}
/>
<label>Include numbers</label>
</div>
</div>
<div>
<div className="checkboxContainer">
<input
type="checkbox"
checked={symbols}
onChange={(e: ChangeEvent<HTMLInputElement>) => {
setSymbols(e.target.checked);
}}
/>
<label>Include symbols (@#$%...)</label>
</div>
<div className="checkboxContainer">
<input
type="checkbox"
checked={similar}
onChange={(e: ChangeEvent<HTMLInputElement>) => {
setSimilar(e.target.checked);
}}
/>
<label>Exclude similar characters</label>
</div>
<div className="checkboxContainer">
<input
type="checkbox"
checked={ambiguous}
onChange={(e: ChangeEvent<HTMLInputElement>) => {
setAmbiguous(e.target.checked);
}}
/>
<label>
Exclude:
&#123;&#125;&#91;&#93;&#40;&#41;&#47;&#92;&#39;&#34;&#96;&#126;&#44;&#59;&#58;&#46;&lt;&gt;
</label>
</div>
</div>
</div>
</div>
<Footer /> <Footer />
</div> </div>
); );

View File

@@ -4,9 +4,16 @@ import "@/assets/styles/footer.scss";
function Footer() { function Footer() {
return ( return (
<footer className="footer"> <footer className="footer">
<p>© 2020 - 2021</p> <div>
<a href="#">Privacy</a> <p>© 2023 - SecureKeyGen.com</p>
<a href="#">Legal Notice</a> </div>
<div>
<a target="_blank" href="https://github.com/DerTyp876/SecureKeyGen">
GitHub
</a>
<a href="/privacy">Privacy</a>
<a href="/legal">Legal Notice</a>
</div>
</footer> </footer>
); );
} }

184
src/Generator.tsx Normal file
View File

@@ -0,0 +1,184 @@
import { ChangeEvent, useEffect, useRef, useState } from "react";
import "@/assets/styles/generator.scss";
import { generatePassword } from "./utils";
const colorWeak = "#eb130c";
const colorGood = "#31f399 ";
const colorBest = "#1fff3d";
export default function Generator() {
const [password, setPassword] = useState("");
const [length, setLength] = useState(64);
const [numbers, setNumbers] = useState(true);
const [symbols, setSymbols] = useState(true);
const [uppercase, setUppercase] = useState(true);
const [lowercase, setLowercase] = useState(true);
const [similar, setSimilar] = useState(false);
const [ambiguous, setAmbiguous] = useState(false);
const copiedTooltipRef = useRef<HTMLDivElement>(null);
const lengthCounterRef = useRef<HTMLInputElement>(null);
function copy() {
navigator.clipboard.writeText(password);
if (copiedTooltipRef.current) {
copiedTooltipRef.current.style.animation = "tooltipAnimation 200ms";
copiedTooltipRef.current.style.opacity = "1";
setTimeout(() => {
if (copiedTooltipRef.current) {
copiedTooltipRef.current.style.opacity = "0";
copiedTooltipRef.current.style.animation = "";
}
}, 1000);
}
}
function generate() {
setPassword(
generatePassword({
length: length,
numbers: numbers,
symbols: symbols,
uppercase: uppercase,
lowercase: lowercase,
excludeSimilar: similar,
excludeAmbiguous: ambiguous,
})
);
}
useEffect(() => {
generate();
}, []);
useEffect(() => {
if (lengthCounterRef.current) {
if (length >= 8 && length <= 16) {
lengthCounterRef.current.style.borderColor = colorWeak;
} else if (length > 16 && length <= 256) {
lengthCounterRef.current.style.borderColor = colorGood;
} else if (length > 256 && length <= 2048) {
lengthCounterRef.current.style.borderColor = colorBest;
}
}
}, [length]);
return (
<div className="generator">
<div id="headline">
<h1>SecureKeyGen</h1>
<h3>Generate secure passwords</h3>
</div>
<div id="content">
<div id="result">
<p id="password">
<code>{password}</code>
</p>
<button onClick={copy} id="copy">
Copy
</button>
<div ref={copiedTooltipRef} id="copiedTooltip">
Copied!
</div>
</div>
<button onClick={generate}>Generate</button>
<div id="length">
<label>Length</label>
<input
onChange={(e: ChangeEvent<HTMLInputElement>) => {
// setLength but clamp it between 8 and 2048
setLength(Math.min(2048, Math.max(8, parseInt(e.target.value))));
}}
type="range"
min="8"
max="2048"
value={length}
/>
<input
type="number"
ref={lengthCounterRef}
onInput={(e: ChangeEvent<HTMLInputElement>) => {
// setLength but clamp it between 8 and 2048
setLength(Math.min(2048, Math.max(8, parseInt(e.target.value))));
}}
value={length}
max={2048}
min={8}
/>
</div>
<div id="checkboxes">
<div>
<div className="checkboxContainer">
<input
type="checkbox"
checked={uppercase}
onChange={(e: ChangeEvent<HTMLInputElement>) => {
setUppercase(e.target.checked);
}}
/>
<label>Include uppercase</label>
</div>
<div className="checkboxContainer">
<input
type="checkbox"
checked={lowercase}
onChange={(e: ChangeEvent<HTMLInputElement>) => {
setLowercase(e.target.checked);
}}
/>
<label>Include lowercase</label>
</div>
<div className="checkboxContainer">
<input
type="checkbox"
checked={numbers}
onChange={(e: ChangeEvent<HTMLInputElement>) => {
setNumbers(e.target.checked);
}}
/>
<label>Include numbers</label>
</div>
</div>
<div>
<div className="checkboxContainer">
<input
type="checkbox"
checked={symbols}
onChange={(e: ChangeEvent<HTMLInputElement>) => {
setSymbols(e.target.checked);
}}
/>
<label>Include symbols (@#$%...)</label>
</div>
<div className="checkboxContainer">
<input
type="checkbox"
checked={similar}
onChange={(e: ChangeEvent<HTMLInputElement>) => {
setSimilar(e.target.checked);
}}
/>
<label>Exclude similar characters</label>
</div>
<div className="checkboxContainer">
<input
type="checkbox"
checked={ambiguous}
onChange={(e: ChangeEvent<HTMLInputElement>) => {
setAmbiguous(e.target.checked);
}}
/>
<label>
Exclude:
&#123;&#125;&#91;&#93;&#40;&#41;&#47;&#92;&#39;&#34;&#96;&#126;&#44;&#59;&#58;&#46;&lt;&gt;
</label>
</div>
</div>
</div>
</div>
</div>
);
}

90
src/Legal.tsx Normal file
View File

@@ -0,0 +1,90 @@
import React from "react";
import "@/assets/styles/legalAndPrivacy.scss";
export default function Legal() {
return (
<div className="legalAndPrivayContainer">
<a href="/">Back to generator</a>
<div className="content">
<h3>Information according to § 5TMG</h3>
<p>
<b>Janis Meister</b>
<br /> SecureKeyGen.com
<br /> Borsigstraße 8<br /> 27574 Bremerhaven
<br /> Germany
<br />
</p>
<h3>Contact</h3>
<p>
E-mail: janis.meister87@gmail.com
<br />
</p>
<h3>EU Dispute Resolution</h3>
<p>
The European Commission provides a platform for online dispute
resolution:
<br />
<a href="https://ec.europa.eu/consumers/odr/">
https://ec.europa.eu/consumers/odr/
</a>
.<br /> You can find our e-mail address in the legal notice above.
<br />
</p>
<h3>Consumer dispute resolution/universal arbitration board</h3>
<p>
We are not willing or obliged to participate in dispute resolution
proceedings
<br /> before a consumer arbitration board.
</p>
<h3>Liability for contents</h3>
<p>
As a service provider, we are responsible for our own content on these
pages under pages according to the general laws. According to §§ 8 to
10 TMG as a service provider, we are not obligated to monitor
transmitted or stored to monitor transmitted or stored third-party
information or to investigate circumstances or to investigate
circumstances that indicate illegal activity.
<br /> <br /> Obligations to remove or block the use of information
according to the general laws remain unaffected. A liability in this
respect liability is only possible from the time of knowledge of a
concrete infringement. infringement is possible. If we become aware of
any such infringements, we will infringements, we will remove this
content immediately.
</p>
<h3>Liability for links</h3>
<p>
Our offer contains links to external websites of third parties, the
contents of which are we have no influence. Therefore, we can for
these foreign contents also take over no guarantee. For the contents
of the linked pages is always the provider or operator of the pages is
responsible for the content of the linked pages. The linked pages were
checked for possible legal violations at the time of linking. checked.
Illegal contents were not recognizable at the time of linking.
recognizable at the time of linking.
<br />
<br /> However, a permanent control of the contents of the linked
pages is not reasonable without concrete evidence of a violation of
the law is not reasonable. In the case of infringements become known,
we will remove such links immediately. remove them.
</p>
<h3>Copyright</h3>
<p>
The contents and works created by the site operators on these pages
are subject to German copyright law. The duplication, processing,
distribution and any kind of exploitation outside the limits of the
copyright copyright require the written consent of the author or
creator. or creator. Downloads and copies of this site are only for
private, non-commercial use.
<br /> <br /> As far as the contents on this page were not created by
the operator, the copyrights of third parties are respected. In
particular, the content of third parties marked as such. Should you
nevertheless become aware of a copyright infringement, we ask for an
appropriate reference. notice. If we become aware of any
infringements, we will remove the respective content remove
immediately.
</p>
</div>
</div>
);
}

606
src/Privacy.tsx Normal file
View File

@@ -0,0 +1,606 @@
import React from "react";
import "@/assets/styles/legalAndPrivacy.scss";
export default function Privacy() {
return (
<div className="legalAndPrivayContainer">
<a href="/">Back to generator</a>
<div className="content">
<h2>1. Data protection at a glance</h2> <h3>General notes</h3>
<p>
The following notes provide a simple overview of what you need to know
happens with your personal data when you visit this website. Personal
data is all data with which you are personally identifiable can be
identified. Detailed information on the topic For data protection,
please refer to our privacy policy listed below this text Privacy
statement.
</p>
<h3>Data collection on this website</h3>
<h4>Who is responsible for data collection on this website?</h4>
<p>
Data processing on this website is carried out by the website
operator. You can find their contact details in the section
&bdquo;Note on the Responsible body&ldquo; in this data protection
statement.
</p>
<h4>How do we collect your data?</h4>
<p>
On the one hand, your data is collected by you providing it to us.
This can be e. g. &nbsp;B. data that you have entered into a Enter
contact form.
</p>
<p>
Other data is collected automatically or after your consent when you
visit the Website is recorded by our IT systems. These are mainly
technical data (e. g. Internet browser, operating system or time of
page view). The collection of this data takes place automatically as
soon as you visit this website enter
</p>
<h4>What do we use your data for?</h4>
<p>
Part of the data is collected in order to ensure error-free provision
of the Website. Other data can be used for the analysis of your User
behavior are used.
</p>
<h4>What rights do you have regarding your data?</h4>
<p>
You have the right at any time, free of charge information &uuml;ber
origin, Recipient and purpose of your stored personal data to receive
You also have the right to request the rectification or L&ouml;schung
of this data to require. When you give consent to You can withdraw
this consent at any time for the future. In addition, you have the
right to request information under the restriction of the processing
of your personal data in certain circumstances personal data.
Furthermore you have a The right to lodge a complaint with the
competent supervisory authority.
</p>
<p>
For this and other questions on the subject of data protection, you
can contact us at contact us at any time.
</p>
<h3>Third-party analytics tools and utilities</h3>
<p>
When visiting this website, your surfing behavior may be statistically
evaluated be This is done mainly with so-called analysis programs.
</p>
<p>
Detailed information on these analysis programs can be found in the
following data protection declaration.
</p>
<h2>2. Hosting</h2>
<p>We host the content of our website with the following provider:</p>
<h3>External hosting</h3>
<p>
This website is hosted externally. The personal data collected on this
website is stored on the servers of the hoster(s). This may include IP
addresses, contact requests, meta and communication data, contractual
data, contact data, names, website accesses and other data generated
via a website.
</p>
<p>
External hosting is carried out for the purpose of contract
fulfillment vis-à-vis our potential and existing customers (Art. 6
para. 1 lit. b DSGVO) and in the interest of a secure, fast and
efficient provision of our online offer by a professional provider
(Art. 6 para. 1 lit. f DSGVO). Insofar as a corresponding consent has
been requested, the processing is carried out exclusively on the basis
of Art. 6 para. 1 lit. a DSGVO and § 25 para. 1 TTDSG, insofar as the
consent includes the storage of cookies or access to information in
the user's terminal device (e.g. device fingerprinting) as defined by
the TTDSG. The consent can be revoked at any time.
</p>
<p>
Our hoster(s) will process your data only to the extent necessary to
fulfill its performance obligations and follow our instructions with
respect to such data.
</p>
<p>We use the following hoster(s):</p>
<p>
Google Firebase: <br /> Google Ireland Limited <br /> Gordon House,
Barrow Street <br /> Dublin 4<br /> Ireland
</p>
<h2>3. General notes and mandatory information</h2> <h3>Privacy</h3>
<p>
The operators of these pages take the protection of your personal data
very seriously. We treat your personal data confidentially and in
accordance with the statutory data protection regulations and this
privacy policy.
</p>
<p>
When you use this website, various personal data are collected.
Personal data is data with which you can be personally identified.
This privacy policy explains what data we collect and what we use it
for. It also explains how and for what purpose this is done.
</p>
<p>
We point out that data transmission over the Internet (e.g.
communication by E-mail) security gaps. A complete protection of the
data against access by third parties is not possible.
</p>
<h3>Note on the responsible entity</h3>
<p>The entity responsible for data processing on this website is:</p>
<p>
<b>Janis Meister</b>
<br /> SecureKeyGen.com
<br /> Borsigstraße 8<br /> 27574 Bremerhaven
<br /> Germany
<br />
</p>
<p>E-mail: janis.meister87@gmail.com</p>
<p>
The controller is the natural or legal person who alone or jointly
with others determines the purposes and means of the processing of
personal data (e.g. names, e-mail addresses, etc.).
</p>
<h3>Storage duration</h3>
<p>
Unless a more specific storage period has been specified within this
privacy policy, your personal data will remain with us until the
purpose for data processing no longer applies. If you assert a
legitimate request for deletion or revoke your consent to data
processing, your data will be deleted unless we have other legally
permissible reasons for storing your personal data (e.g. retention
periods under tax or commercial law); in the latter case, the data
will be deleted once these reasons no longer apply.
</p>
<h3>
General information on the legal basis for data processing on this
website
</h3>
<p>
If you have consented to data processing, we process your personal
data on the basis of Art. 6 (1) a DSGVO or Art. 9 (2) a DSGVO, if
special categories of data are processed according to Art. 9 (1)
DSGVO. In the case of explicit consent to the transfer of personal
data to third countries, the data processing is also based on Art. 49
(1) a DSGVO. If you have consented to the storage of cookies or to the
access to information in your terminal device (e.g. via device
fingerprinting), the data processing is additionally carried out on
the basis of Section 25 (1) TTDSG. The consent can be revoked at any
time. If your data is required for the performance of a contract or
for the implementation of pre-contractual measures, we process your
data on the basis of Art. 6 para. 1 lit. b DSGVO. Furthermore, if your
data is required for the fulfillment of a legal obligation, we process
it on the basis of Art. 6 para. 1 lit. c DSGVO. Furthermore, the data
processing may be carried out on the basis of our legitimate interest
according to Art. 6 para. 1 lit. f DSGVO. Information about the
relevant legal basis in each individual case is provided in the
following paragraphs of this privacy policy.
</p>
<h3>Note on data transfer to the USA and other third countries</h3>
<p>
Among other things, we use tools from companies based in the USA or
other third countries that are not secure under data protection law.
If these tools are active, your personal data may be transferred to
these third countries and processed there. We would like to point out
that no level of data protection comparable to that in the EU can be
guaranteed in these countries. For example, US companies are obliged
to hand over personal data to security authorities without you as a
data subject being able to take legal action against this. It can
therefore not be ruled out that US authorities (e.g. intelligence
services) process, evaluate and permanently store your data located on
US servers for monitoring purposes. We have no influence on these
processing activities.
</p>
<h3>Revocation of your consent to data processing</h3>
<p>
Many data processing operations are only possible with your express
consent. You can revoke consent you have already given at any time.
The legality of the data processing carried out until the revocation
remains unaffected by the revocation.
</p>
<h3>
Right to object to data collection in special cases and to direct
marketing (Art. 21 DSGVO)
</h3>
<p>
IF THE DATA PROCESSING IS CARRIED OUT ON THE BASIS OF ART. 6 ABS. 1
LIT. E OR F DSGVO, YOU HAVE THE RIGHT TO OBJECT TO THE PROCESSING OF
YOUR PERSONAL DATA AT ANY TIME FOR REASONS ARISING FROM YOUR
PARTICULAR SITUATION; THIS ALSO APPLIES TO PROFILING BASED ON THESE
PROVISIONS. THE RESPECTIVE LEGAL BASIS ON WHICH PROCESSING IS BASED
CAN BE FOUND IN THIS PRIVACY POLICY. IF YOU OBJECT, WE WILL NO LONGER
PROCESS YOUR PERSONAL DATA CONCERNED UNLESS WE CAN DEMONSTRATE
COMPELLING LEGITIMATE GROUNDS FOR THE PROCESSING WHICH OVERRIDE YOUR
INTERESTS, RIGHTS AND FREEDOMS, OR THE PROCESSING IS FOR THE PURPOSE
OF ASSERTING, EXERCISING OR DEFENDING LEGAL CLAIMS (OBJECTION UNDER
ARTICLE 21(1) DSGVO).
</p>
<p>
IF YOUR PERSONAL DATA ARE PROCESSED FOR THE PURPOSE OF DIRECT
MARKETING, YOU HAVE THE RIGHT TO OBJECT AT ANY TIME TO THE PROCESSING
OF PERSONAL DATA CONCERNING YOU FOR THE PURPOSE OF SUCH MARKETING;
THIS ALSO APPLIES TO PROFILING INSOFAR AS IT IS RELATED TO SUCH DIRECT
MARKETING. IF YOU OBJECT, YOUR PERSONAL DATA WILL SUBSEQUENTLY NO
LONGER BE USED FOR THE PURPOSE OF DIRECT MARKETING (OBJECTION PURSUANT
TO ARTICLE 21 (2) DSGVO).
</p>
<h3>Right of appeal to the competent supervisory authority</h3>
<p>
In the event of breaches of the GDPR, data subjects shall have a right
of appeal to a supervisory authority, in particular in the Member
State of their habitual residence, their place of work or the place of
the alleged breach. The right of appeal is without prejudice to other
administrative or judicial remedies.
</p>
<h3>Right to data portability</h3>
<p>
You have the right to have data that we process automatically on the
basis of your consent or in fulfillment of a contract handed over to
you or to a third party in a common, machine-readable format. If you
request the direct transfer of the data to another controller, this
will only be done insofar as it is technically feasible.
</p>
<h3>Information, deletion and correction</h3>
<p>
Within the framework of the applicable legal provisions, you have the
right at any time to free information about your stored personal data,
its origin and recipient and the purpose of data processing and, if
necessary, a right to correction or deletion of this data. For this
purpose, as well as for further questions on the subject of personal
data, you can contact us at any time.
</p>
<h3>Right to restriction of processing</h3>
<p>
You have the right to request the restriction of the processing of
your personal data. For this purpose, you can contact us at any time.
The right to restriction of processing exists in the following cases:
</p>
<ul>
<li>
If you dispute the accuracy of your personal data stored by us, we
usually need time to verify this. For the duration of the review,
you have the right to request the restriction of the processing of
your personal data.
</li>
<li>
If the processing of your personal data happened/is happening
unlawfully, you may request the restriction of data processing
instead of erasure.
</li>
<li>
If we no longer need your personal data, but you need it to
exercise, defend or enforce legal claims, you have the right to
request restriction of the processing of your personal data instead
of deletion.
</li>
<li>
If you have lodged an objection pursuant to Art. 21 (1) DSGVO, a
balancing of your and our interests must be carried out. As long as
it has not yet been determined whose interests prevail, you have the
right to request the restriction of the processing of your personal
data.
</li>
</ul>
<p>
If you have restricted the processing of your personal data, this data
may - apart from being stored - only be processed with your consent or
for the assertion, exercise or defense of legal claims or for the
protection of the rights of another natural or legal person or for
reasons of an important public interest of the European Union or a
Member State.
</p>
<h3>SSL or TLS encryption</h3>
<p>
This site uses SSL or TLS encryption for security reasons and to
protect the transmission of confidential content, such as orders or
requests that you send to us as the site operator. You can recognize
an encrypted connection by the fact that the address line of the
browser changes from "http://" to "https://" and by the lock symbol in
your browser line.
</p>
<p>
If SSL or TLS encryption is activated, the data you transmit to us
cannot be read by third parties.
</p>
<h2>4. Data collection on this website</h2> <h3>Cookies</h3>
<p>
Our Internet pages use so-called "cookies". Cookies are small data
packets and do not cause any damage to your end device. They are
stored either temporarily for the duration of a session (session
cookies) or permanently (permanent cookies) on your end device.
Session cookies are automatically deleted at the end of your visit.
Permanent cookies remain stored on your end device until you delete
them yourself or until they are automatically deleted by your web
browser.
</p>
<p>
In some cases, cookies from third-party companies may also be stored
on your terminal device when you enter our site (third-party cookies).
These enable us or you to use certain services of the third-party
company (e.g. cookies for processing payment services).
</p>
<p>
Cookies have various functions. Many cookies are technically
necessary, as certain website functions would not work without them
(e.g. the shopping cart function or the display of videos). Other
cookies are used to evaluate user behavior or display advertising.
</p>
<p>
Cookies are used to evaluate user behavior or display advertising.
Cookies that are necessary to carry out the electronic communication
process, to provide certain functions that you have requested (e.g.
for the shopping cart function) or to optimize the website (e.g.
cookies to measure the web audience) (necessary cookies) are stored on
the basis of Art. 6 (1) lit. f DSGVO, unless another legal basis is
specified. The website operator has a legitimate interest in storing
necessary cookies for the technically error-free and optimized
provision of its services. If consent to the storage of cookies and
comparable recognition technologies has been requested, the processing
is based exclusively on this consent (Art. 6 para. 1 lit. a DSGVO and
§ 25 para. 1 TTDSG); the consent can be revoked at any time.
</p>
<p>
You can set your browser so that you are informed about the setting of
cookies and only allow cookies in individual cases, exclude the
acceptance of cookies for certain cases or in general and activate the
automatic deletion of cookies when closing the browser. When
deactivating cookies, the functionality of this website may be
limited.
</p>
<p>
If cookies are used by third-party companies or for analysis purposes,
we will inform you about this separately within the framework of this
data protection declaration and, if necessary, request your consent.
</p>
<h2>5. Social media</h2> <h3>Instagram</h3>
<p>
Functions of the Instagram service are integrated on this website.
These functions are offered by Meta Platforms Ireland Limited, 4 Grand
Canal Square, Grand Canal Harbour, Dublin 2, Ireland.
</p>
<p>
When the social media element is active, a direct connection is
established between your end device and the Instagram server.
Instagram thereby receives information about your visit to this
website.
</p>
<p>
Wenn Sie in Ihrem Instagram-Account eingeloggt sind, k&ouml;nnen Sie
durch Anklicken des Instagram-Buttons die Inhalte dieser Website mit
Ihrem Instagram-Profil verlinken. Dadurch kann Instagram den Besuch
dieser Website Ihrem Benutzerkonto zuordnen. Wir weisen darauf hin,
dass wir als Anbieter der Seiten keine Kenntnis vom Inhalt der
&uuml;bermittelten Daten sowie deren Nutzung durch Instagram erhalten.
</p>
<p>
If you are logged into your Instagram account, you can link the
content of this website to your Instagram profile by clicking on the
Instagram button. This allows Instagram to associate your visit to
this website with your user account. We would like to point out that
we, as the provider of the pages, have no knowledge of the content of
the transmitted data or its use by Instagram.
</p>
<p>
Insofar as consent has been obtained, the above-mentioned service is
used on the basis of Art. 6 Para. 1 lit. a DSGVO and § 25 TTDSG. The
consent can be revoked at any time. Insofar as no consent has been
obtained, the use of the service is based on our legitimate interest
in achieving the greatest possible visibility in social media. Insofar
as personal data is collected on our website with the help of the tool
described here and forwarded to Facebook or Instagram, we and Meta
Platforms Ireland Limited, 4 Grand Canal Square, Grand Canal Harbour,
Dublin 2, Ireland are jointly responsible for this data processing
(Art. 26 DSGVO). The joint responsibility is limited exclusively to
the collection of the data and its forwarding to Facebook or
Instagram. The processing by Facebook or Instagram that takes place
after the forwarding is not part of the joint responsibility. The
obligations incumbent on us jointly have been set out in a joint
processing agreement. You can find the text of the agreement at:
<a
href="https://www.facebook.com/legal/controller_addendum"
target="_blank"
rel="noopener noreferrer"
>
https://www.facebook.com/legal/controller_addendum
</a>
. According to this agreement, we are responsible for providing the
privacy information when using the Facebook or Instagram tool and for
the privacy-secure implementation of the tool on our website. Facebook
is responsible for the data security of the Facebook or Instagram
products. You can assert data subject rights (e.g. requests for
information) regarding the data processed by Facebook or Instagram
directly with Facebook. If you assert the data subject rights with us,
we are obliged to forward them to Facebook.
</p>
<p>
Data transfer to the USA is based on the standard contractual clauses
of the EU Commission. Details can be found here:
<a
href="https://www.facebook.com/legal/EU_data_transfer_addendum"
target="_blank"
rel="noopener noreferrer"
>
https://www.facebook.com/legal/EU_data_transfer_addendum
</a>
,
<a
href="https://help.instagram.com/519522125107875"
target="_blank"
rel="noopener noreferrer"
>
https://help.instagram.com/519522125107875
</a>
and
<a
href="https://de-de.facebook.com/help/566994660333381"
target="_blank"
rel="noopener noreferrer"
>
https://de-de.facebook.com/help/566994660333381
</a>
.
</p>
<p>
For more information, please see Instagram's privacy policy:
<a
href="https://instagram.com/about/legal/privacy/"
target="_blank"
rel="noopener noreferrer"
>
https://instagram.com/about/legal/privacy/
</a>
.
</p>
<h2>6. Plugins and tools</h2> <h3>Google Fonts (locally hosted)</h3>
<p>
This site uses for the uniform representation of fonts so-called
Google Fonts, which are provided by Google. The Google Fonts are
installed locally. A connection to Google servers does not take place.
take place.
</p>
<p>
For more information about Google Fonts, see
<a
href="https://developers.google.com/fonts/faq"
target="_blank"
rel="noopener noreferrer"
>
https://developers.google.com/fonts/faq
</a>
and in the privacy policy of Google:
<a
href="https://policies.google.com/privacy?hl=de"
target="_blank"
rel="noopener noreferrer"
>
https://policies.google.com/privacy?hl=de
</a>
.
</p>
<h3>Font Awesome (locally hosted)</h3>
<p>
This site uses Font Awesome for consistent font rendering. Font
Awesome is installed locally. A connection to servers of Fonticons,
Inc. does not take place.
</p>
<p>
For more information about Font Awesome, please see the Font Awesome
Privacy Policy at:
<a
href="https://fontawesome.com/privacy"
target="_blank"
rel="noopener noreferrer"
>
https://fontawesome.com/privacy
</a>
.
</p>
<h3>Google Maps</h3>
<p>
This site uses the map service Google Maps. The provider is Google
Ireland Limited ("Google"), Gordon House, Barrow Street, Dublin 4,
Ireland.
</p>
<p>
To use the functions of Google Maps, it is necessary to store your IP
address. This information is usually transferred to a Google server in
the USA and stored there. The provider of this site has no influence
on this data transmission. If Google Maps is activated, Google may use
Google Fonts for the purpose of uniform display of fonts. When calling
up Google Maps, your browser loads the required web fonts into its
browser cache in order to display texts and fonts correctly.
</p>
<p>
The use of Google Maps is in the interest of an appealing presentation
of our online offers and an easy location of the places indicated by
us on the website. This represents a legitimate interest within the
meaning of Art. 6 para. 1 lit. f DSGVO. If a corresponding consent has
been requested, the processing is carried out exclusively on the basis
of Art. 6 para. 1 lit. a DSGVO and § 25 para. 1 TTDSG, insofar as the
consent includes the storage of cookies or access to information in
the user's terminal device (e.g. device fingerprinting) within the
meaning of the TTDSG. The consent can be revoked at any time.
</p>
<p>
Data transfer to the USA is based on the standard contractual clauses
of the EU Commission. Details can be found here:
<a
href="https://privacy.google.com/businesses/gdprcontrollerterms/"
target="_blank"
rel="noopener noreferrer"
>
https://privacy.google.com/businesses/gdprcontrollerterms/
</a>
and
<a
href="https://privacy.google.com/businesses/gdprcontrollerterms/sccs/"
target="_blank"
rel="noopener noreferrer"
>
https://privacy.google.com/businesses/gdprcontrollerterms/sccs/
</a>
.
</p>
<p>
More information on the handling of user data can be found in Google's
privacy policy:
<a
href="https://policies.google.com/privacy?hl=de"
target="_blank"
rel="noopener noreferrer"
>
https://policies.google.com/privacy?hl=de
</a>
.
</p>
<h3>Google reCAPTCHA</h3>
<p>
We use "Google reCAPTCHA" (hereinafter "reCAPTCHA") on this website.
The provider is Google Ireland Limited ("Google"), Gordon House,
Barrow Street, Dublin 4, Ireland.
</p>
<p>
The purpose of reCAPTCHA is to check whether the data input on this
website (e.g. in a contact form) is made by a human or by an automated
program. For this purpose, reCAPTCHA analyzes the behavior of the
website visitor based on various characteristics. This analysis begins
automatically as soon as the website visitor enters the website. For
the analysis, reCAPTCHA evaluates various information (e.g. IP
address, time spent by the website visitor on the website or mouse
movements made by the user). The data collected during the analysis is
forwarded to Google.
</p>
<p>
The reCAPTCHA analyses run completely in the background. Website
visitors are not notified that an analysis is taking place.
</p>
<p>
The storage and analysis of the data is based on Art. 6 para. 1 lit. f
DSGVO. The website operator has a legitimate interest in protecting
its web offers from abusive automated spying and from SPAM. If a
corresponding consent has been requested, the processing is carried
out exclusively on the basis of Art. 6 para. 1 lit. a DSGVO and § 25
para. 1 TTDSG, insofar as the consent includes the storage of cookies
or access to information in the user's terminal device (e.g. device
fingerprinting) as defined by the TTDSG. The consent can be revoked at
any time.
</p>
<p>
For more information about Google reCAPTCHA, please see the Google
Privacy Policy and the Google Terms of Service at the following links:
<a
href="https://policies.google.com/privacy?hl=de"
target="_blank"
rel="noopener noreferrer"
>
https://policies.google.com/privacy?hl=de
</a>
and
<a
href="https://policies.google.com/terms?hl=de"
target="_blank"
rel="noopener noreferrer"
>
https://policies.google.com/terms?hl=de
</a>
.
</p>
<p>
Source:
<a href="https://www.e-recht24.de">https://www.e-recht24.de</a>
</p>
</div>
</div>
);
}

View File

@@ -1,214 +1,26 @@
// Breakpoints
$breakpoint-1: 760px;
$breakpoint-2: 565px;
@keyframes tooltipAnimation {
0% {
opacity: 0;
transform: translateY(-10px);
}
100% {
opacity: 1;
transform: translateY(0);
}
}
.app { .app {
margin-top: 30px;
justify-content: center;
align-items: center;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
row-gap: 50px; row-gap: 30px;
justify-content: center;
align-items: center;
}
#headline { a {
text-align: center; text-decoration: none;
} transition: all 100ms linear;
color: #1fcf7d;
#content { &:hover {
display: flex; color: #1dff95;
flex-direction: column; }
align-items: center; }
justify-content: center;
row-gap: 50px; a:visited {
color: #8d8d8d;
button { text-decoration: none;
background-color: #202024; transition: all 100ms linear;
color: #fff; &:hover {
font-weight: bold; color: #1dff95;
border: 2px solid #31f399;
border-radius: 5px;
padding: 10px 20px;
cursor: pointer;
transition: all 300ms ease-in-out;
&:hover {
background-color: #42d486;
color: #202024;
}
}
#length {
display: flex;
flex-direction: row;
align-items: center;
justify-content: center;
column-gap: 20px;
@media screen and (max-width: $breakpoint-2) {
column-gap: 10px;
}
label {
font-size: 1.2rem;
font-weight: bold;
@media screen and (max-width: $breakpoint-2) {
font-size: 0.8rem;
}
}
input[type="number"] {
-webkit-appearance: none;
-moz-appearance: none;
appearance: none;
padding: 5px 5px;
border: 2px solid #31f399;
border-radius: 5px;
background-color: #202024;
color: #fff;
font-size: 1.2rem;
font-weight: bold;
text-align: center;
outline: none;
transition: all 200ms ease-in-out;
cursor: text;
&::-webkit-inner-spin-button,
&::-webkit-outer-spin-button {
-webkit-appearance: none;
margin: 0;
}
}
}
#result {
display: flex;
flex-direction: row;
align-items: center;
justify-content: center;
column-gap: 20px;
position: relative;
#password {
white-space: nowrap;
overflow: auto;
font-size: 1.2rem;
font-weight: bold;
width: 500px;
padding-bottom: 10px;
@media screen and (max-width: $breakpoint-1) {
width: 300px;
}
@media screen and (max-width: $breakpoint-2) {
width: 200px;
}
}
#copy {
padding: 5px 10px;
border: 2px solid #31f39973;
transition: all 100ms ease-in-out;
&:hover {
border-color: #42d486;
background-color: transparent;
color: #fff;
}
}
#copiedTooltip {
opacity: 0;
position: absolute;
right: -90px;
background-color: #31f399;
color: #202024;
padding: 5px 10px;
border-radius: 5px;
font-size: 0.8rem;
font-weight: bold;
}
}
#checkboxes {
display: flex;
flex-direction: row;
flex-wrap: wrap;
justify-content: space-between;
align-items: center;
column-gap: 80px;
row-gap: 20px;
@media screen and (max-width: $breakpoint-2) {
flex-direction: row;
justify-content: center;
align-items: center;
}
div {
display: flex;
flex-direction: column;
row-gap: 20px;
.checkboxContainer {
display: flex;
flex-direction: row;
align-items: center;
justify-content: left;
column-gap: 10px;
input {
-webkit-appearance: none;
-moz-appearance: none;
appearance: none;
width: 20px;
height: 20px;
border: 2px solid #31f399;
border-radius: 5px;
background-color: #202024;
outline: none;
transition: all 200ms ease-in-out;
position: relative;
// make it a cross when checked
&:checked {
&:after {
content: "";
position: absolute;
width: 10px;
height: 2px;
background-color: #31f399;
transform: rotate(45deg);
}
&:before {
content: "";
position: absolute;
width: 10px;
height: 2px;
background-color: #31f399;
transform: rotate(-45deg);
}
&:after,
&:before {
top: 7px;
left: 3px;
}
}
cursor: pointer;
}
label {
cursor: pointer;
}
}
}
}
} }
} }

View File

@@ -1,29 +1,37 @@
.footer { .footer {
display: flex; display: flex;
flex-direction: row; flex-direction: row;
column-gap: 20px; column-gap: 30px;
justify-content: center; justify-content: center;
color: #8d8d8d; color: #8d8d8d;
padding: 20px;
text-align: center; text-align: center;
position: fixed; padding-bottom: 30px;
bottom: 0;
width: 100%; width: 100%;
a { @media screen and (max-width: 550px) {
text-decoration: none; flex-direction: column;
transition: all 100ms linear;
&:hover {
color: #31f399;
}
} }
a:visited { div {
color: #8d8d8d; a {
text-decoration: none; text-decoration: none;
transition: all 100ms linear; transition: all 100ms linear;
&:hover { color: #8d8d8d;
color: #31f399; margin-inline: 10px;
&:hover {
color: #31f399;
}
}
a:visited {
color: #8d8d8d;
text-decoration: none;
transition: all 100ms linear;
&:hover {
color: #31f399;
}
} }
} }
} }

View File

@@ -0,0 +1,214 @@
// Breakpoints
$breakpoint-1: 760px;
$breakpoint-2: 565px;
@keyframes tooltipAnimation {
0% {
opacity: 0;
transform: translateY(-10px);
}
100% {
opacity: 1;
transform: translateY(0);
}
}
.generator {
margin-top: 30px;
justify-content: center;
align-items: center;
display: flex;
flex-direction: column;
row-gap: 50px;
#headline {
text-align: center;
}
#content {
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
row-gap: 50px;
button {
background-color: #202024;
color: #fff;
font-weight: bold;
border: 2px solid #31f399;
border-radius: 5px;
padding: 10px 20px;
cursor: pointer;
transition: all 300ms ease-in-out;
&:hover {
background-color: #42d486;
color: #202024;
}
}
#length {
display: flex;
flex-direction: row;
align-items: center;
justify-content: center;
column-gap: 20px;
@media screen and (max-width: $breakpoint-2) {
column-gap: 10px;
}
label {
font-size: 1.2rem;
font-weight: bold;
@media screen and (max-width: $breakpoint-2) {
font-size: 0.8rem;
}
}
input[type="number"] {
-webkit-appearance: none;
-moz-appearance: none;
appearance: none;
padding: 5px 5px;
border: 2px solid #31f399;
border-radius: 5px;
background-color: #202024;
color: #fff;
font-size: 1.2rem;
font-weight: bold;
text-align: center;
outline: none;
transition: all 200ms ease-in-out;
cursor: text;
&::-webkit-inner-spin-button,
&::-webkit-outer-spin-button {
-webkit-appearance: none;
margin: 0;
}
}
}
#result {
display: flex;
flex-direction: row;
align-items: center;
justify-content: center;
column-gap: 20px;
position: relative;
#password {
white-space: nowrap;
overflow: auto;
font-size: 1.2rem;
font-weight: bold;
width: 500px;
padding-bottom: 10px;
@media screen and (max-width: $breakpoint-1) {
width: 300px;
}
@media screen and (max-width: $breakpoint-2) {
width: 200px;
}
}
#copy {
padding: 5px 10px;
border: 2px solid #31f39973;
transition: all 100ms ease-in-out;
&:hover {
border-color: #42d486;
background-color: transparent;
color: #fff;
}
}
#copiedTooltip {
opacity: 0;
position: absolute;
right: -90px;
background-color: #31f399;
color: #202024;
padding: 5px 10px;
border-radius: 5px;
font-size: 0.8rem;
font-weight: bold;
}
}
#checkboxes {
display: flex;
flex-direction: row;
flex-wrap: wrap;
justify-content: space-between;
align-items: center;
column-gap: 80px;
row-gap: 20px;
@media screen and (max-width: $breakpoint-2) {
flex-direction: row;
justify-content: center;
align-items: center;
}
div {
display: flex;
flex-direction: column;
row-gap: 20px;
.checkboxContainer {
display: flex;
flex-direction: row;
align-items: center;
justify-content: left;
column-gap: 10px;
input {
-webkit-appearance: none;
-moz-appearance: none;
appearance: none;
width: 20px;
height: 20px;
border: 2px solid #31f399;
border-radius: 5px;
background-color: #202024;
outline: none;
transition: all 200ms ease-in-out;
position: relative;
// make it a cross when checked
&:checked {
&:after {
content: "";
position: absolute;
width: 10px;
height: 2px;
background-color: #31f399;
transform: rotate(45deg);
}
&:before {
content: "";
position: absolute;
width: 10px;
height: 2px;
background-color: #31f399;
transform: rotate(-45deg);
}
&:after,
&:before {
top: 7px;
left: 3px;
}
}
cursor: pointer;
}
label {
cursor: pointer;
}
}
}
}
}
}

View File

@@ -0,0 +1,42 @@
.legalAndPrivayContainer {
width: 100%;
padding-top: 20px;
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
h1 {
text-align: center;
padding-top: 10px;
padding-bottom: 20px;
}
// Back to home button
& > a {
text-decoration: none;
transition: all 100ms linear;
color: #1fcf7d;
padding: 20px 30px;
&:hover {
color: #1dff95;
}
}
.content {
width: 80%;
display: block;
margin-left: auto;
margin-right: auto;
font-size: 14pt;
text-align: left;
line-height: 2em;
letter-spacing: 1px;
text-overflow: clip;
word-wrap: break-word;
h3,
h2 {
margin-top: 20px;
margin-bottom: 10px;
}
}
}