-
- Share ideas and upvote others
-
-
-
-
-
-
- Discussions
-
+
+
+
+
+
+
Just code it
+
+ Not another no-code wizardry. You know how to code, so go ahead and
+ do it.
+
+
+
+
+
+
+
+
Be (really) free
+
+ Self-hosted, Open Source and Local-first. Easy to enter, easy to
+ leave.
+
-
+
+
+
+
+
+
+
+
+
+
+
+
🙏 We need your honest feedback
+
+
+ CASE is still in its early days and has much room to improve. If you
+ also think we deserve a hassle-free backend, here's how you can lend
+ us a hand:
+
+
+ Try CASE using the npx
command.
+ Leave your feedback (good or bad) on Github Discussions .
+ If you want to follow the progress, star us on Github .
+
+
+
+
+
+ Something is not working ? Contact us through our Discord support channel
+
+
+
+
+
+
+
diff --git a/src/app/pages/home/home.component.scss b/src/app/pages/home/home.component.scss
index ae2e6ad..eea824b 100644
--- a/src/app/pages/home/home.component.scss
+++ b/src/app/pages/home/home.component.scss
@@ -8,7 +8,7 @@
img {
position: relative;
left: 50%;
- transform:translateX(-50%);
+ transform: translateX(-50%);
min-width: unset;
width: unset;
max-width: unset;
@@ -16,27 +16,21 @@
}
.bg-shape {
- position: absolute;
+ position: absolute;
top: 50%;
left: 50%;
- transform:translate(-50%, -50%);
+ transform: translate(-50%, -50%);
z-index: -1;
}
-.versus {
- em {
- margin-right: 4px;
- color: $warning;
- -webkit-text-stroke: .5px black;
-
- }
-}
figure.main-pic {
position: relative;
+
img {
position: relative;
z-index: 1;
border: 1px solid $border-color;
+ border-radius: 24px;
}
}
@@ -46,8 +40,9 @@ figure.main-pic {
transform: translateY(-50%);
width: 65.93%;
height: 86.36%;
+
div {
- translate: none;
+ translate: none;
rotate: none;
scale: none;
transform: translate(0px, 0px);
@@ -58,35 +53,41 @@ figure.main-pic {
border-radius: 16px;
filter: blur(45px);
will-change: transform;
-}
+ }
&-left {
left: 36px;
+
div {
background: $primary;
}
}
+
&-right {
right: 36px;
+
div {
background: $success;
}
}
}
-.buttons .button {
+.buttons .button {
z-index: 1;
}
.npx-wrapper {
position: relative;
+
.is-copied {
position: absolute;
- opacity: 0;
+ opacity: 0;
+
&.is-active {
@extend .slideInUp;
}
}
+
.button-copy {
opacity: 1;
@@ -96,10 +97,11 @@ figure.main-pic {
}
}
-.button-copy, .is-copied {
+.button-copy,
+.is-copied {
display: inline-block;
- min-width: 81px;
- white-space: nowrap;
+ min-width: 81px;
+ white-space: nowrap;
}
.slideInUp {
@@ -109,71 +111,72 @@ figure.main-pic {
animation-duration: .5s;
-webkit-animation-fill-mode: both;
animation-fill-mode: both;
- }
- @-webkit-keyframes slideInUp {
- 0% {
- -webkit-transform: translateY(100%);
- transform: translateY(100%);
- opacity: 0
-
- }
-
- 100% {
- -webkit-transform: translateY(0);
- transform: translateY(0);
- opacity: 1;
- }
- }
+}
- @keyframes slideInUp {
- 0% {
- -webkit-transform: translateY(100%);
- transform: translateY(100%);
- opacity: 0
+@-webkit-keyframes slideInUp {
+ 0% {
+ -webkit-transform: translateY(100%);
+ transform: translateY(100%);
+ opacity: 0
+ }
+ 100% {
+ -webkit-transform: translateY(0);
+ transform: translateY(0);
+ opacity: 1;
+ }
}
-100% {
--webkit-transform: translateY(0);
-transform: translateY(0);
-opacity: 1;
-}
+@keyframes slideInUp {
+ 0% {
+ -webkit-transform: translateY(100%);
+ transform: translateY(100%);
+ opacity: 0
+ }
+
+ 100% {
+ -webkit-transform: translateY(0);
+ transform: translateY(0);
+ opacity: 1;
+ }
}
.slideOutUp {
--webkit-animation-name: slideOutUp;
-animation-name: slideOutUp;
--webkit-animation-duration: .5s;
-animation-duration: .5s;
--webkit-animation-fill-mode: both;
-animation-fill-mode: both;
+ -webkit-animation-name: slideOutUp;
+ animation-name: slideOutUp;
+ -webkit-animation-duration: .5s;
+ animation-duration: .5s;
+ -webkit-animation-fill-mode: both;
+ animation-fill-mode: both;
}
+
@-webkit-keyframes slideOutUp {
-0% {
--webkit-transform: translateY(0);
-transform: translateY(0);
-opacity: 1
+ 0% {
+ -webkit-transform: translateY(0);
+ transform: translateY(0);
+ opacity: 1
+ }
+ 100% {
+ -webkit-transform: translateY(-100%);
+ transform: translateY(-100%);
+ opacity: 0;
+ }
}
-100% {
--webkit-transform: translateY(-100%);
-transform: translateY(-100%);
-opacity: 0;
-}
-}
+
@keyframes slideOutUp {
-0% {
--webkit-transform: translateY(0);
-transform: translateY(0);
-opacity: 1
+ 0% {
+ -webkit-transform: translateY(0);
+ transform: translateY(0);
+ opacity: 1
+ }
-}
-100% {
- -webkit-transform: translateY(-100%);
- transform: translateY(-100%);
- opacity: 0;
+ 100% {
+ -webkit-transform: translateY(-100%);
+ transform: translateY(-100%);
+ opacity: 0;
}
}
@@ -184,18 +187,21 @@ opacity: 1
.install-code {
white-space: nowrap;
+
@include touch {
font-size: $size-7;
}
}
.has-icon-left {
---star-width: 24px;
---star-margin: 9px;
+ --star-width: 24px;
+ --star-margin: 9px;
+
span:first-child {
margin-right: var(--star-margin);
width: var(--star-width);
}
+
span:last-child {
width: calc(100% - var(--star-width));
}
@@ -210,5 +216,200 @@ opacity: 1
background-image: url('/assets/images/stars.svg');
background-repeat: no-repeat;
background-size: 40%;
- background-position: 100% 55%;
+ background-position: 100% 55%;
+}
+
+.illu {
+ position: absolute;
+ top: -48px;
+ left: $gap;
+ border-radius: $radius-large;
+ height: 96px;
+ width: 96px;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+
+ img {
+ width: 67%;
+ height: auto;
+ }
+
+}
+
+.col-left {
+ @include touch {
+ padding-top: 3rem;
+ }
+}
+
+.col-right {
+ @include touch {
+ padding-top: 7rem;
+ }
+}
+
+app-admin-panel-hero {
+ display: flex;
+ width: 100%;
+ height: 100%;
+}
+
+.circle {
+ position: relative;
+ top: -1px;
+ width: 9px;
+ height: 9px;
+ border-radius: 50%;
+ background-color: $grey-darker;
+ margin-left: 9px;
+ transition: all .2s ease-in-out;
+
+ &.is-active {
+ background-color: $success;
+ box-shadow: rgba(0, 0, 0, 0.2) 0 -1px 7px 1px, inset #304701 0 -1px 2px, $success 0 2px 12px;
+ }
+}
+
+
+.icon-wrapper {
+ width: 54px;
+ height: 54px;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+
+ &.has-background-primary-light {
+ &.is-bordered {
+ border-color: rgba($primary, 0.5);
+ }
+
+ i {
+ background: -webkit-linear-gradient($primary, #5065FF);
+ -webkit-background-clip: text;
+ -webkit-text-fill-color: transparent;
+ }
+ }
+
+ &.has-background-success-light {
+ &.is-bordered {
+ border-color: rgba($success, 0.5);
+ }
+
+ i {
+ background: -webkit-linear-gradient(rgba($success-dark, 0.8), $success-dark);
+ -webkit-background-clip: text;
+ -webkit-text-fill-color: transparent;
+ }
+ }
+}
+
+.count-wrapper {
+ position: relative;
+ overflow: hidden;
+ min-width: 46px;
+ max-width: 46px;
+
+ &:before {
+ content: '';
+ position: absolute;
+ display: inline-block;
+ bottom: 0;
+ left: 0;
+ width: 1px;
+ height: calc(100% - 36px);
+ background: $grey-lighter;
+ }
+}
+
+.square {
+ width: 12px;
+ min-width: 12px;
+ height: 12px;
+ background: $success;
+ background: linear-gradient(90deg, rgba($success, 1) 0%, rgba($link, 1) 100%);
+ margin-right: 6px;
+ margin-top: 14px;
+
+ + span {
+ position: relative;
+ top: -12px;
+ padding-right: 18px;
+ }
+}
+
+.columns--features {
+ background: rgb(20, 47, 78);
+ background: linear-gradient(28deg, rgba($white-ter, 0.1) 0%, rgba($white, .5) 50%, rgba($white-ter, 0.4) 100%);
+ border-top: 1px solid $grey-lighter;
+ border-left: 1px solid $grey-lighter;
+}
+
+.column--feature {
+ border-bottom: 1px solid $grey-lighter;
+ border-right: 1px solid $grey-lighter;
+}
+
+
+.shake {
+ -webkit-animation-name: shake;
+ animation-name: shake;
+ -webkit-animation-duration: 8s;
+ animation-duration: 8s;
+
+ -webkit-animation-fill-mode: both;
+ animation-fill-mode: both;
+ animation-iteration-count: infinite;
+}
+
+@-webkit-keyframes shake {
+
+ 0%,
+ 10% {
+ -webkit-transform: translate3d(0, 0, 0);
+ transform: translate3d(0, 0, 0);
+ }
+
+ 1%,
+ 3%,
+ 5%,
+ 7%,
+ 9% {
+ -webkit-transform: translate3d(-5px, 0, 0);
+ transform: translate3d(-5px, 0, 0);
+ }
+
+ 2%,
+ 4%,
+ 6%,
+ 8% {
+ -webkit-transform: translate3d(5px, 0, 0);
+ transform: translate3d(5px, 0, 0);
+ }
+}
+
+@keyframes shake {
+
+ 0%,
+ 10% {
+ -webkit-transform: translate3d(0, 0, 0);
+ transform: translate3d(0, 0, 0);
+ }
+
+ 1%,
+ 3%,
+ 5%,
+ 7%,
+ 9% {
+ -webkit-transform: translate3d(-5px, 0, 0);
+ transform: translate3d(-5px, 0, 0);
+ }
+
+ 2%,
+ 4%,
+ 6%,
+ 8% {
+ -webkit-transform: translate3d(5px, 0, 0);
+ transform: translate3d(5px, 0, 0);
+ }
}
diff --git a/src/app/pages/home/home.component.ts b/src/app/pages/home/home.component.ts
index e15321c..234f70e 100644
--- a/src/app/pages/home/home.component.ts
+++ b/src/app/pages/home/home.component.ts
@@ -8,22 +8,24 @@ import { Meta, Title } from '@angular/platform-browser'
})
export class HomeComponent {
isCopied = false
+ isDemoMenuOpen = false
+ isApiWindow = false
constructor(meta: Meta, title: Title) {
- title.setTitle('CASE - Develop a CRUD web app in 15 minutes 🚀')
+ title.setTitle('CASE - A complete backend without leaving your IDE 🚀')
meta.addTag({
name: 'og:title',
- content: 'CASE - Develop a CRUD web app in 15 minutes 🚀'
+ content: 'CASE - A complete backend without leaving your IDE 🚀'
})
meta.addTag({
name: 'description',
content:
- 'CASE allows developers to install, develop and deploy a crud app in minutes'
+ 'CASE is a Typescript lightweight BaaS (Backend As A Service) requiring minimal coding.'
})
meta.addTag({
name: 'og:description',
content:
- 'CASE allows developers to install, develop and deploy a crud app in minutes'
+ 'CASE is a Typescript lightweight BaaS (Backend As A Service) requiring minimal coding.'
})
meta.addTag({ name: 'og:url', content: 'https://case.app' })
meta.addTag({
@@ -33,7 +35,7 @@ export class HomeComponent {
meta.addTag({
name: 'keywords',
content:
- 'CASE, Typescript, Javascript,Admin panel, Dashboard, ERP, Business app, Business application, Business software, APIs, Business tool, CMS, Frameworkless, CRUD app, CLI, ERP, Custom web app'
+ 'BaaS, Typescript, Javascript, Admin panel, Dashboard, ERP, Business app, Business application, Business software, APIs, CRUD app, CLI, ERP, Custom web app'
})
}
diff --git a/src/app/partials/admin-panel-hero/admin-panel-hero.component.cy.ts b/src/app/partials/admin-panel-hero/admin-panel-hero.component.cy.ts
new file mode 100644
index 0000000..d1a4c10
--- /dev/null
+++ b/src/app/partials/admin-panel-hero/admin-panel-hero.component.cy.ts
@@ -0,0 +1,7 @@
+import { AdminPanelHeroComponent } from './admin-panel-hero.component'
+
+describe('AdminPanelHeroComponent', () => {
+ it('should mount', () => {
+ cy.mount(AdminPanelHeroComponent)
+ })
+})
\ No newline at end of file
diff --git a/src/app/partials/admin-panel-hero/admin-panel-hero.component.html b/src/app/partials/admin-panel-hero/admin-panel-hero.component.html
new file mode 100644
index 0000000..dd7ea68
--- /dev/null
+++ b/src/app/partials/admin-panel-hero/admin-panel-hero.component.html
@@ -0,0 +1,830 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/src/app/partials/admin-panel-hero/admin-panel-hero.component.scss b/src/app/partials/admin-panel-hero/admin-panel-hero.component.scss
new file mode 100644
index 0000000..7b6eca0
--- /dev/null
+++ b/src/app/partials/admin-panel-hero/admin-panel-hero.component.scss
@@ -0,0 +1,542 @@
+@import '../../../styles/variables/all';
+@import 'bulma/sass/utilities/mixins';
+
+$width-emails: 219px !default;
+$width-positions: 178px !default;
+
+$avatar-x-01: -404px !default;
+$avatar-x-02: -224px !default;
+$avatar-x-03: 0 !default;
+
+$button-x-01: -398px !default;
+$button-x-02: -219px !default;
+$button-x-03: 0 !default;
+
+$duration-scale: 6s !default;
+$delay-scale: 4.63s !default;
+
+$duration-text: 0.3s !default;
+$delay-text: #{$delay-scale + $duration-scale * 0.4} !default;
+$animation-text: cubic-bezier(.09, .86, .52, 1.39) !default;
+
+$duration-link: $duration-text !default;
+$delay-link: #{$delay-scale + $duration-scale * 0.79 + 1.12s} !default;
+$animation-link: $animation-text !default;
+
+.svg-container {
+ width: 100%;
+ height: 100%;
+
+ > svg {
+ width: 100%;
+ }
+}
+
+svg {
+ width: 100%;
+ height: auto;
+ border: 2px solid $border-color;
+ border-radius: $radius-large;
+ background-image: url('/assets/images/user-list-v.svg');
+ background-color: $white;
+ background-repeat: no-repeat;
+ background-size: contain;
+}
+
+
+#animation-wrapper {
+ transform: scale(1);
+ transition: all 0.3s ease-out;
+ backface-visibility: visible;
+ -webkit-animation-name: scale;
+ animation-name: scale;
+ -webkit-animation-duration: $duration-scale;
+ animation-duration: $duration-scale;
+ -webkit-animation-delay: $delay-scale;
+ animation-delay: $delay-scale;
+ -webkit-animation-fill-mode: both;
+ animation-fill-mode: both;
+ -webkit-animation-timing-function: ease-out;
+ animation-timing-function: ease-out;
+}
+
+#col-emails {
+ transform: translateX(#{-1 * $width-emails});
+
+ transition: all 0.3s ease-in-out;
+ -webkit-animation-name: emails-displayed;
+ animation-name: emails-displayed;
+ -webkit-animation-duration: $duration-scale;
+ animation-duration: $duration-scale;
+ -webkit-animation-delay: $delay-scale;
+ animation-delay: $delay-scale;
+ -webkit-animation-fill-mode: both;
+ animation-fill-mode: both;
+ -webkit-animation-timing-function: ease-out;
+ animation-timing-function: ease-out;
+
+ .text-dark {
+ opacity: 0;
+ transform: translateY(5px);
+ transition: all 0.3s ease-in-out;
+ -webkit-animation-name: text-dark;
+ animation-name: text-dark;
+ -webkit-animation-duration: $duration-text;
+ animation-duration: $duration-text;
+ -webkit-animation-fill-mode: both;
+ animation-fill-mode: both;
+ -webkit-animation-timing-function: $animation-text;
+ animation-timing-function: $animation-text;
+
+ @for $i from 1 through 10 {
+ &-#{$i} {
+ -webkit-animation-delay: calc(#{$i * 0.02s} + #{$delay-text});
+ animation-delay: calc(#{$i * 0.02s} + #{$delay-text});
+ }
+ }
+ }
+}
+
+#col-positions {
+ transform: translateX(#{-1 * $width-positions});
+ opacity: 0;
+ transition: all 0.3s ease-in-out;
+ -webkit-animation-name: positions-displayed;
+ animation-name: positions-displayed;
+ -webkit-animation-duration: $duration-scale;
+ animation-duration: $duration-scale;
+ -webkit-animation-delay: $delay-scale;
+ animation-delay: $delay-scale;
+ -webkit-animation-fill-mode: both;
+ animation-fill-mode: both;
+ -webkit-animation-timing-function: ease-out;
+ animation-timing-function: ease-out;
+
+ .text-link {
+ opacity: 0;
+ transform: translateY(5px);
+ transition: all 0.3s ease-in-out;
+ -webkit-animation-name: text-link;
+ animation-name: text-link;
+ -webkit-animation-duration: $duration-link;
+ animation-duration: $duration-link;
+ -webkit-animation-fill-mode: both;
+ animation-fill-mode: both;
+ -webkit-animation-timing-function: $animation-link;
+ animation-timing-function: $animation-link;
+
+ @for $i from 1 through 10 {
+ &-#{$i} {
+ -webkit-animation-delay: calc(#{$i * 0.02s} + #{$delay-link});
+ animation-delay: calc(#{$i * 0.02s} + #{$delay-link});
+ }
+ }
+ }
+}
+
+#col-ends {
+ transform: translateX(#{-1 * $width-positions - $width-emails});
+ transition: all 0.3s ease-in-out;
+ -webkit-animation-name: col-ends-x;
+ animation-name: col-ends-x;
+ -webkit-animation-duration: $duration-scale;
+ animation-duration: $duration-scale;
+ -webkit-animation-delay: $delay-scale;
+ animation-delay: $delay-scale;
+ -webkit-animation-fill-mode: both;
+ animation-fill-mode: both;
+ -webkit-animation-timing-function: ease-out;
+ animation-timing-function: ease-out;
+}
+
+#header-right-part {
+ transform: translateX(#{$avatar-x-01});
+ transition: all 0.3s ease-in-out;
+ -webkit-animation-name: avatar-x;
+ animation-name: avatar-x;
+ -webkit-animation-duration: $duration-scale;
+ animation-duration: $duration-scale;
+ -webkit-animation-delay: $delay-scale;
+ animation-delay: $delay-scale;
+ -webkit-animation-fill-mode: both;
+ animation-fill-mode: both;
+ -webkit-animation-timing-function: ease-out;
+ animation-timing-function: ease-out;
+}
+
+#button {
+ transform: translateX(#{$button-x-01});
+ transition: all 0.3s ease-in-out;
+ -webkit-animation-name: button-x;
+ animation-name: button-x;
+ -webkit-animation-duration: $duration-scale;
+ animation-duration: $duration-scale;
+ -webkit-animation-delay: 4.63s;
+ animation-delay: 4.63s;
+ -webkit-animation-fill-mode: both;
+ animation-fill-mode: both;
+ -webkit-animation-timing-function: ease-out;
+ animation-timing-function: ease-out;
+}
+
+
+@-webkit-keyframes scale {
+ 0% {
+ -webkit-transform: scale(1);
+ transform: scale(1);
+ }
+
+ 40% {
+ -webkit-transform: scale(.8);
+ transform: scale(.8);
+ }
+
+ 79% {
+ -webkit-transform: scale(.8);
+ transform: scale(.8);
+ }
+
+ 100% {
+ -webkit-transform: scale(.6567);
+ transform: scale(.6567);
+ }
+}
+
+@keyframes scale {
+ 0% {
+ -webkit-transform: scale(1);
+ transform: scale(1);
+ }
+
+ 40% {
+ -webkit-transform: scale(.8);
+ transform: scale(.8);
+ }
+
+ 79% {
+ -webkit-transform: scale(.8);
+ transform: scale(.8);
+ }
+
+ 100% {
+ -webkit-transform: scale(.6567);
+ transform: scale(.6567);
+ }
+}
+
+
+
+@-webkit-keyframes emails-displayed {
+ 0% {
+ -webkit-transform: translateX(#{-1 * $width-emails});
+ transform: translateX(#{-1 * $width-emails});
+
+
+ }
+
+ 40% {
+ -webkit-transform: translateX(0);
+ transform: translateX(0);
+
+ }
+
+ 100% {
+ -webkit-transform: translateX(0);
+ transform: translateX(0);
+
+ }
+}
+
+@keyframes emails-displayed {
+ 0% {
+ -webkit-transform: translateX(#{-1 * $width-emails});
+
+
+ transform: translateX(#{-1 * $width-emails});
+
+ }
+
+ 40% {
+ -webkit-transform: translateX(0);
+ transform: translateX(0);
+
+ }
+
+ 100% {
+ -webkit-transform: translateX(0);
+
+ transform: translateX(0);
+ }
+}
+
+
+@-webkit-keyframes positions-displayed {
+ 0% {
+ -webkit-transform: translateX(#{-1 * $width-positions});
+ transform: translateX(#{-1 * $width-positions});
+ opacity: 0;
+
+ }
+
+ 40% {
+ -webkit-transform: translateX(#{-1 * $width-positions});
+ transform: translateX(#{-1 * $width-positions});
+ opacity: 1;
+ }
+
+ 79% {
+ -webkit-transform: translateX(#{-1 * $width-positions});
+ transform: translateX(#{-1 * $width-positions});
+ opacity: 1;
+ }
+
+ 100% {
+ -webkit-transform: translateX(0);
+ transform: translateX(0);
+ opacity: 1;
+
+ }
+}
+
+@keyframes positions-displayed {
+ 0% {
+ -webkit-transform: translateX(#{-1 * $width-positions});
+ transform: translateX(#{-1 * $width-positions});
+ opacity: 0;
+ }
+
+ 40% {
+ -webkit-transform: translateX(#{-1 * $width-positions});
+ transform: translateX(#{-1 * $width-positions});
+ opacity: 1;
+ }
+
+ 79% {
+ -webkit-transform: translateX(#{-1 * $width-positions});
+ transform: translateX(#{-1 * $width-positions});
+ opacity: 1;
+ }
+
+ 100% {
+ -webkit-transform: translateX(0);
+ opacity: 1;
+ transform: translateX(0);
+ }
+}
+
+@-webkit-keyframes col-ends-x {
+ 0% {
+ -webkit-transform: translateX(#{-1 * $width-positions - $width-emails});
+ transform: translateX(#{-1 * $width-positions - $width-emails});
+ }
+
+ 40% {
+ -webkit-transform: translateX(#{-1 * $width-emails});
+ transform: translateX(#{-1 * $width-emails});
+
+ }
+
+ 79% {
+ -webkit-transform: translateX(#{-1 * $width-emails});
+ transform: translateX(#{-1 * $width-emails});
+
+ }
+
+ 100% {
+ -webkit-transform: translateX(0);
+ transform: translateX(0);
+
+ }
+}
+
+@keyframes col-ends-x {
+ 0% {
+ -webkit-transform: translateX(#{-1 * $width-positions - $width-emails});
+ transform: translateX(#{-1 * $width-positions - $width-emails});
+
+ }
+
+ 40% {
+ -webkit-transform: translateX(#{-1 * $width-emails});
+ transform: translateX(#{-1 * $width-emails});
+
+ }
+
+ 79% {
+ -webkit-transform: translateX(#{-1 * $width-emails});
+ transform: translateX(#{-1 * $width-emails});
+
+ }
+
+ 100% {
+ -webkit-transform: translateX(0);
+ transform: translateX(0);
+
+ }
+}
+
+@-webkit-keyframes button-x {
+ 0% {
+ -webkit-transform: translateX(#{$button-x-01});
+ transform: translateX(#{$button-x-01});
+ }
+
+ 40% {
+ -webkit-transform: translateX(#{$button-x-02});
+ transform: translateX(#{$button-x-02});
+ }
+
+ 79% {
+ -webkit-transform: translateX(#{$button-x-02});
+ transform: translateX(#{$button-x-02});
+ }
+
+ 100% {
+ -webkit-transform: translateX(#{$button-x-03});
+ transform: translateX(#{$button-x-03});
+
+ }
+}
+
+@keyframes button-x {
+ 0% {
+ -webkit-transform: translateX(#{$button-x-01});
+ transform: translateX(#{$button-x-01});
+
+ }
+
+ 40% {
+ -webkit-transform: translateX(#{$button-x-02});
+ transform: translateX(#{$button-x-02});
+ }
+
+ 79% {
+ -webkit-transform: translateX(#{$button-x-02});
+ transform: translateX(#{$button-x-02});
+ }
+
+ 100% {
+ -webkit-transform: translateX(#{$button-x-03});
+ transform: translateX(#{$button-x-03});
+
+ }
+}
+
+@-webkit-keyframes avatar-x {
+ 0% {
+ -webkit-transform: translateX(#{$button-x-01});
+ transform: translateX(#{$button-x-01});
+ }
+
+ 40% {
+ -webkit-transform: translateX(#{$button-x-02});
+ transform: translateX(#{$button-x-02});
+ }
+
+ 79% {
+ -webkit-transform: translateX(#{$button-x-02});
+ transform: translateX(#{$button-x-02});
+ }
+
+ 100% {
+ -webkit-transform: translateX(#{$button-x-03});
+ transform: translateX(#{$button-x-03});
+ }
+}
+
+@keyframes avatar-x {
+ 0% {
+ -webkit-transform: translateX(#{$button-x-01});
+ transform: translateX(#{$button-x-01});
+
+ }
+
+ 40% {
+ -webkit-transform: translateX(#{$button-x-02});
+ transform: translateX(#{$button-x-02});
+ }
+
+ 79% {
+ -webkit-transform: translateX(#{$button-x-02});
+ transform: translateX(#{$button-x-02});
+ }
+
+ 100% {
+ -webkit-transform: translateX(#{$button-x-03});
+ transform: translateX(#{$button-x-03});
+ }
+}
+
+@-webkit-keyframes text-dark {
+ 0% {
+ -webkit-transform: translateY(5px);
+ transform: translateY(5px);
+ opacity: 0;
+ }
+
+ 100% {
+ -webkit-transform: translateY(0);
+ transform: translateY(0);
+
+ opacity: 1;
+ }
+}
+
+@keyframes text-dark {
+ 0% {
+ -webkit-transform: translateY(5px);
+ transform: translateY(5px);
+ opacity: 0;
+
+ }
+
+ 100% {
+ -webkit-transform: translateY(0);
+ transform: translateY(0);
+ opacity: 1;
+ }
+}
+
+@-webkit-keyframes text-link {
+ 0% {
+ -webkit-transform: translateY(5px);
+ transform: translateY(5px);
+ opacity: 0;
+ }
+
+ 79% {
+ -webkit-transform: translateY(5px);
+ transform: translateY(5px);
+ opacity: 0;
+
+ }
+
+
+ 100% {
+ -webkit-transform: translateY(0);
+ transform: translateY(0);
+
+ opacity: 1;
+ }
+}
+
+@keyframes text-link {
+ 0% {
+ -webkit-transform: translateY(5px);
+ transform: translateY(5px);
+ opacity: 0;
+ }
+
+ 79% {
+ -webkit-transform: translateY(5px);
+ transform: translateY(5px);
+ opacity: 0;
+
+ }
+
+ 100% {
+ -webkit-transform: translateY(0);
+ transform: translateY(0);
+ opacity: 1;
+ }
+}
diff --git a/src/app/partials/admin-panel-hero/admin-panel-hero.component.ts b/src/app/partials/admin-panel-hero/admin-panel-hero.component.ts
new file mode 100644
index 0000000..6ca728b
--- /dev/null
+++ b/src/app/partials/admin-panel-hero/admin-panel-hero.component.ts
@@ -0,0 +1,10 @@
+import { Component } from '@angular/core';
+
+@Component({
+ selector: 'app-admin-panel-hero',
+ templateUrl: './admin-panel-hero.component.html',
+ styleUrls: ['./admin-panel-hero.component.scss']
+})
+export class AdminPanelHeroComponent {
+
+}
diff --git a/src/app/partials/api-hero/api-hero.component.cy.ts b/src/app/partials/api-hero/api-hero.component.cy.ts
new file mode 100644
index 0000000..0dd6b7e
--- /dev/null
+++ b/src/app/partials/api-hero/api-hero.component.cy.ts
@@ -0,0 +1,7 @@
+import { ApiHeroComponent } from './api-hero.component'
+
+describe('ApiHeroComponent', () => {
+ it('should mount', () => {
+ cy.mount(ApiHeroComponent)
+ })
+})
\ No newline at end of file
diff --git a/src/app/partials/api-hero/api-hero.component.html b/src/app/partials/api-hero/api-hero.component.html
new file mode 100644
index 0000000..10b6db2
--- /dev/null
+++ b/src/app/partials/api-hero/api-hero.component.html
@@ -0,0 +1,23 @@
+
+
+
+ GET
+ http://localhost:4000/api/dynamic/users/10
+
+
+ Status:
+ 200 OK
+
+
+
+ {
+ "id" : 10,
+ "name" : "Carla Levin",
+ "email" : "carla.levin@icloud.com",
+ "position" : {
+ "id" : 4,
+ "name" : "IT architect",
+ }
+ }
+
+
diff --git a/src/app/partials/api-hero/api-hero.component.scss b/src/app/partials/api-hero/api-hero.component.scss
new file mode 100644
index 0000000..30ba458
--- /dev/null
+++ b/src/app/partials/api-hero/api-hero.component.scss
@@ -0,0 +1,97 @@
+@import '../../../styles/variables/all';
+@import 'bulma/sass/utilities/mixins';
+
+pre {
+ border-bottom-left-radius: $radius-large;
+ border-bottom-right-radius: $radius-large;
+}
+
+.api-display {
+ opacity: 0;
+ transform: translateY(5px);
+ height: 0;
+ -webkit-animation-name: api-display;
+ animation-name: api-display;
+ -webkit-animation-duration: 0.3s;
+ animation-duration: 0.3s;
+ -webkit-animation-fill-mode: both;
+ animation-fill-mode: both;
+ -webkit-animation-timing-function: ease-out;
+ animation-timing-function: ease-out;
+
+ &--01 {
+ -webkit-animation-delay: 3.5s;
+ animation-delay: 3.5s;
+ }
+
+ &--02 {
+ -webkit-animation-delay: 9s;
+ animation-delay: 9s;
+ }
+}
+
+
+@-webkit-keyframes api-display {
+ 0% {
+ -webkit-transform: translateY(5px);
+ transform: translateY(5px);
+ opacity: 0;
+ display: none;
+ background-color: transparent;
+ }
+
+ 60% {
+ background-color: rgba($success, .36);
+ display: inline;
+ }
+
+ 100% {
+ -webkit-transform: translateY(0);
+ transform: translateY(0);
+ opacity: 1;
+ background-color: transparent;
+ }
+}
+
+@keyframes api-display {
+ 0% {
+ -webkit-transform: translateY(5px);
+ transform: translateY(5px);
+ opacity: 0;
+ display: none;
+ background-color: transparent;
+ }
+
+ 60% {
+ background-color: rgba($success, .36);
+ display: inline;
+ }
+
+ 100% {
+ -webkit-transform: translateY(0);
+ transform: translateY(0);
+ opacity: 1;
+ background-color: transparent;
+ }
+}
+
+
+.top-bar {
+ border-top-left-radius: $radius-large;
+ border-top-right-radius: $radius-large;
+ background-color: $dark;
+ padding: #{$column-gap / 2} $column-gap;
+
+ > div:first-child {
+ flex-grow: 1
+ }
+}
+
+.endpoint-request {
+ border-radius: 100px;
+ border: 0.5px solid $grey-darker;
+ background-color: $black-ter;
+ color: $grey-lighter;
+ padding: 6px #{$column-gap / 1.5};
+ width: 100%;
+}
diff --git a/src/app/partials/api-hero/api-hero.component.ts b/src/app/partials/api-hero/api-hero.component.ts
new file mode 100644
index 0000000..d64147b
--- /dev/null
+++ b/src/app/partials/api-hero/api-hero.component.ts
@@ -0,0 +1,10 @@
+import { Component } from '@angular/core';
+
+@Component({
+ selector: 'app-api-hero',
+ templateUrl: './api-hero.component.html',
+ styleUrls: ['./api-hero.component.scss']
+})
+export class ApiHeroComponent {
+
+}
diff --git a/src/app/partials/header/header.component.html b/src/app/partials/header/header.component.html
index 467d3b4..0ccb4ef 100644
--- a/src/app/partials/header/header.component.html
+++ b/src/app/partials/header/header.component.html
@@ -3,6 +3,7 @@
+`
diff --git a/src/app/partials/header/header.component.scss b/src/app/partials/header/header.component.scss
index e69de29..cea4dd1 100644
--- a/src/app/partials/header/header.component.scss
+++ b/src/app/partials/header/header.component.scss
@@ -0,0 +1,4 @@
+.beta {
+ position: relative;
+ top: -7px;
+}
diff --git a/src/app/partials/header/header.component.ts b/src/app/partials/header/header.component.ts
index 966dff7..b1c56d6 100644
--- a/src/app/partials/header/header.component.ts
+++ b/src/app/partials/header/header.component.ts
@@ -1,4 +1,4 @@
-import { Component, OnInit } from '@angular/core'
+import { Component, ElementRef, HostListener, OnInit } from '@angular/core'
import { NavigationEnd, Router } from '@angular/router'
@Component({
@@ -8,8 +8,9 @@ import { NavigationEnd, Router } from '@angular/router'
})
export class HeaderComponent implements OnInit {
currentPath: string
+ isDemoMenuOpen = false
- constructor(private router: Router) {}
+ constructor(private router: Router, private elementRef: ElementRef) {}
ngOnInit(): void {
this.router.events.subscribe((routeChanged) => {
@@ -18,4 +19,11 @@ export class HeaderComponent implements OnInit {
}
})
}
+
+ @HostListener('document:click', ['$event.target'])
+ clickOut(eventTarget: HTMLElement) {
+ if (!this.elementRef.nativeElement.contains(eventTarget)) {
+ this.isDemoMenuOpen = false
+ }
+ }
}
diff --git a/src/app/partials/live-code-hero/live-code-hero.component.html b/src/app/partials/live-code-hero/live-code-hero.component.html
new file mode 100644
index 0000000..810e75c
--- /dev/null
+++ b/src/app/partials/live-code-hero/live-code-hero.component.html
@@ -0,0 +1,64 @@
+
diff --git a/src/app/partials/live-code-hero/live-code-hero.component.scss b/src/app/partials/live-code-hero/live-code-hero.component.scss
new file mode 100644
index 0000000..ce3a91c
--- /dev/null
+++ b/src/app/partials/live-code-hero/live-code-hero.component.scss
@@ -0,0 +1,82 @@
+@import '../../../styles/variables/all';
+@import 'bulma/sass/utilities/mixins';
+
+.box {
+ --code-color: #b3bbc7;
+ --sidebar-width: 40px;
+ --sidebar-padding: 10px;
+ --header-padding: 10px 10px;
+
+ &--code {
+ width: 100%;
+ background-color: $black-ter;
+ color: var(--code-color);
+ text-align: left;
+
+ &__head {
+ padding: var(--header-padding);
+ }
+
+ &__sidebar {
+ width: var(--sidebar-width);
+ padding-right: var(--sidebar-padding);
+ line-height: 1.589;
+ color: $grey;
+ }
+
+ &__body {
+ pre {
+ color: var(--code-color);
+ }
+ }
+
+ &__content {
+ padding-left: var(--sidebar-padding);
+
+ }
+ }
+}
+
+pre {
+ padding: 0;
+}
+
+#typewriter {
+ font-family: $family-code;
+
+ &:after {
+ content: '|';
+ color: $white;
+ animation: blink 500ms linear infinite alternate;
+ }
+}
+
+@-webkit-keyframes blink {
+ 0% {
+ opacity: 0;
+ }
+
+ 100% {
+ opacity: 1;
+ }
+}
+
+@-moz-keyframes blink {
+ 0% {
+ opacity: 0;
+ }
+
+ 100% {
+ opacity: 1;
+ }
+}
+
+@keyframes blink {
+ 0% {
+ opacity: 0;
+ }
+
+ 100% {
+ opacity: 1;
+ }
+}
diff --git a/src/app/partials/live-code-hero/live-code-hero.component.spec.ts b/src/app/partials/live-code-hero/live-code-hero.component.spec.ts
new file mode 100644
index 0000000..2e01877
--- /dev/null
+++ b/src/app/partials/live-code-hero/live-code-hero.component.spec.ts
@@ -0,0 +1,7 @@
+import { LiveCodeHeroComponent } from './live-code-hero.component'
+
+describe('LiveCodeHeroComponent', () => {
+ it('should mount', () => {
+ cy.mount(LiveCodeHeroComponent)
+ })
+})
\ No newline at end of file
diff --git a/src/app/partials/live-code-hero/live-code-hero.component.ts b/src/app/partials/live-code-hero/live-code-hero.component.ts
new file mode 100644
index 0000000..85c50da
--- /dev/null
+++ b/src/app/partials/live-code-hero/live-code-hero.component.ts
@@ -0,0 +1,78 @@
+import { Component, ElementRef, ViewChild } from '@angular/core'
+
+@Component({
+ selector: 'app-live-code-hero',
+ templateUrl: './live-code-hero.component.html',
+ styleUrls: ['./live-code-hero.component.scss']
+})
+export class LiveCodeHeroComponent {
+ @ViewChild('typewriter', { static: true }) typewriter: ElementRef
+
+ ngOnInit(): void {
+ var typer = this.setupTypewriter(this.typewriter.nativeElement)
+
+ typer.type()
+ }
+
+ setupTypewriter(t: any) {
+ var HTML = t.innerHTML
+
+ t.innerHTML = ''
+
+ var cursorPosition = 0,
+ tag: any = '',
+ writingTag = false,
+ tagOpen = false,
+ typeSpeed = 5,
+ tempTypeSpeed = 0
+
+ var type = function () {
+ if (writingTag === true) {
+ tag += HTML[cursorPosition]
+ }
+
+ if (HTML[cursorPosition] === '<') {
+ tempTypeSpeed = 0
+ if (tagOpen) {
+ tagOpen = false
+ writingTag = true
+ } else {
+ tag = ''
+ tagOpen = true
+ writingTag = true
+ tag += HTML[cursorPosition]
+ }
+ }
+ if (!writingTag && tagOpen) {
+ tag.innerHTML += HTML[cursorPosition]
+ }
+ if (!writingTag && !tagOpen) {
+ if (HTML[cursorPosition] === ' ') {
+ tempTypeSpeed = 0
+ } else {
+ tempTypeSpeed = Math.random() * typeSpeed + 20
+ }
+ t.innerHTML += HTML[cursorPosition]
+ }
+ if (writingTag === true && HTML[cursorPosition] === '>') {
+ tempTypeSpeed = Math.random() * typeSpeed + 20
+ writingTag = false
+ if (tagOpen) {
+ var newSpan = document.createElement('span')
+ t.appendChild(newSpan)
+ newSpan.innerHTML = tag
+ tag = newSpan.firstChild
+ }
+ }
+
+ cursorPosition += 1
+ if (cursorPosition < HTML.length - 1) {
+ setTimeout(type, tempTypeSpeed)
+ }
+ }
+
+ return {
+ type: type
+ }
+ }
+}
diff --git a/src/app/partials/sdk-features/sdk-features.component.cy.ts b/src/app/partials/sdk-features/sdk-features.component.cy.ts
new file mode 100644
index 0000000..ef53b8a
--- /dev/null
+++ b/src/app/partials/sdk-features/sdk-features.component.cy.ts
@@ -0,0 +1,7 @@
+import { SdkFeaturesComponent } from './sdk-features.component'
+
+describe('SdkFeaturesComponent', () => {
+ it('should mount', () => {
+ cy.mount(SdkFeaturesComponent)
+ })
+})
\ No newline at end of file
diff --git a/src/app/partials/sdk-features/sdk-features.component.html b/src/app/partials/sdk-features/sdk-features.component.html
new file mode 100644
index 0000000..558d3b7
--- /dev/null
+++ b/src/app/partials/sdk-features/sdk-features.component.html
@@ -0,0 +1,140 @@
+
diff --git a/src/app/partials/sdk-features/sdk-features.component.scss b/src/app/partials/sdk-features/sdk-features.component.scss
new file mode 100644
index 0000000..be30a32
--- /dev/null
+++ b/src/app/partials/sdk-features/sdk-features.component.scss
@@ -0,0 +1,8 @@
+@import '../../../styles/variables/all';
+@import 'bulma/sass/utilities/mixins';
+
+.tab-content {
+ @include fullhd {
+ min-height: 456.27px;
+ }
+}
diff --git a/src/app/partials/sdk-features/sdk-features.component.ts b/src/app/partials/sdk-features/sdk-features.component.ts
new file mode 100644
index 0000000..1e0facd
--- /dev/null
+++ b/src/app/partials/sdk-features/sdk-features.component.ts
@@ -0,0 +1,10 @@
+import { Component } from '@angular/core';
+
+@Component({
+ selector: 'app-sdk-features',
+ templateUrl: './sdk-features.component.html',
+ styleUrls: ['./sdk-features.component.scss']
+})
+export class SdkFeaturesComponent {
+ selectedTab = 'fetch'
+}
diff --git a/src/assets/images/Pages/user-list-v 1.svg b/src/assets/images/Pages/user-list-v 1.svg
new file mode 100644
index 0000000..d11c1a6
--- /dev/null
+++ b/src/assets/images/Pages/user-list-v 1.svg
@@ -0,0 +1,670 @@
+
diff --git a/src/assets/images/admin-panel.mov b/src/assets/images/admin-panel.mov
new file mode 100644
index 0000000..3d59659
Binary files /dev/null and b/src/assets/images/admin-panel.mov differ
diff --git a/src/assets/images/admin-panel.mp4 b/src/assets/images/admin-panel.mp4
new file mode 100644
index 0000000..cbcb7ab
Binary files /dev/null and b/src/assets/images/admin-panel.mp4 differ
diff --git a/src/assets/images/admin-panel.webm b/src/assets/images/admin-panel.webm
new file mode 100644
index 0000000..b988dce
Binary files /dev/null and b/src/assets/images/admin-panel.webm differ
diff --git a/src/assets/images/angular.svg b/src/assets/images/angular.svg
index 367953e..46f557f 100644
--- a/src/assets/images/angular.svg
+++ b/src/assets/images/angular.svg
@@ -1,4 +1,5 @@
-