2023-11-02 21:44:14 +01:00
{% extends "main.html" %}
<!-- Render hero under tabs -->
{% block tabs %}
{{ super() }}
<!-- Additional styles for landing page -->
< style >
/* Apply box shadow on smaller screens that don't display tabs */
@ media only screen and ( max-width : 1220px ) {
. md-header {
box-shadow : 0 0 .2 rem rgba ( 0 , 0 , 0 , .1 ), 0 .2 rem .4 rem rgba ( 0 , 0 , 0 , .2 );
transition : color 250 ms , background-color 250 ms , box-shadow 250 ms ;
}
}
/* Hide main content for now */
. md-content {
display : none ;
}
/* Hide table of contents */
@ media screen and ( min-width : 60em ) {
. md-sidebar--secondary {
display : none ;
}
}
/* Hide navigation */
@ media screen and ( min-width : 76 . 25em ) {
. md-sidebar--primary {
display : none ;
}
}
/* Get started button */
. md-typeset . md-button--primary {
color : var ( -- md - primary - fg - color );
background-color : var ( -- md - primary - bg - color );
border-color : var ( -- md - primary - bg - color );
}
. md-typeset . md-button--primary : hover {
color : var ( -- md - primary - bg - color );
background-color : var ( -- md - primary - fg - color );
border-color : var ( -- md - primary - bg - color );
}
. tx-hero {
max-width : 700 px ;
display : flex ;
padding : .4 rem ;
margin : 0 auto ;
text-align : center ;
}
. tx-hero h1 {
font-weight : 700 ;
font-size : 38 px ;
line-height : 46 px ;
color : rgb ( 38 , 38 , 38 );
}
. tx-hero p {
color : rgb ( 92 , 92 , 92 );
font-weight : 400 ;
font-size : 20 px ;
line-height : 32 px ;
}
. tx-hero__image {
max-width : 1000 px ;
min-width : 600 px ;
width : 100 % ;
height : auto ;
margin : 0 auto ;
display : flex ;
align-items : stretch ;
}
. tx-hero__image img {
width : 100 % ;
height : 100 % ;
min-width : 0 ;
}
/* Secondary content styles */
. secondary-section {
background : rgb ( 245 , 245 , 245 ) none repeat scroll 0 % 0 % ;
border-top : 1 px solid rgb ( 222 , 222 , 222 );
border-bottom : 1 px solid rgb ( 222 , 222 , 222 )
}
@ media screen and ( max-width : 1012px ) {
. secondary-section {
display : block ;
}
}
. secondary-section . g {
position : relative ;
margin-left : auto ;
margin-right : auto ;
padding : 0 px 40 px ;
max-width : 1280 px ;
}
. secondary-section . g . section {
font-size : 18 px ;
font-weight : 400 ;
line-height : 30 px ;
letter-spacing : normal ;
padding : 88 px 0 px 116 px ;
}
. secondary-section . g . section . follow {
padding-top : 0 px ;
}
. secondary-section . g . section . component-wrapper {
display : flex ;
-moz- box-align : center ;
align-items : center ;
}
@ media screen and ( max-width : 1012px ) {
. secondary-section . g . section . component-wrapper {
display : block ;
}
}
. secondary-section . g . section . component-wrapper h3 {
color : rgb ( 38 , 38 , 38 );
font-size : 36 px ;
font-weight : 700 ;
line-height : 46 px ;
letter-spacing : normal ;
margin-bottom : 12 px ;
}
. secondary-section . g . section . component-wrapper h4 {
color : rgb ( 38 , 38 , 38 );
}
. secondary-section . g . section . component-wrapper p {
color : rgb ( 92 , 92 , 92 );
font-size : 18 px ;
font-weight : 400 ;
line-height : 30 px ;
letter-spacing : normal ;
margin-bottom : 16 px ;
}
. secondary-section . g . section . component-wrapper . image-wrapper {
margin-bottom : 12 px ;
overflow : hidden ;
border-radius : 8 px ;
margin-top : 48 px ;
border : 1 px solid rgb ( 222 , 222 , 222 );
box-shadow : rgba ( 202 , 202 , 202 , 0.15 ) 0 px 0 px 0 px 6 px ;
max-width : 600 px ;
width : 100 % ;
height : auto ;
margin : 0 auto ;
display : flex ;
align-items : stretch ;
}
. image-wrapper img {
width : 100 % ;
height : 100 % ;
min-width : 0 ;
}
. secondary-section . g . section . component-wrapper . first-column {
padding-right : 100 px ;
flex : 0 1 auto ;
height : auto ;
width : 50 % ;
}
@ media screen and ( max-width : 1012px ) {
. secondary-section . g . section . component-wrapper . first-column {
padding-right : 0 px ;
width : 100 % ;
margin-bottom : 32 px ;
}
}
. secondary-section . g . section . component-wrapper . second-column {
flex : 0 1 auto ;
height : auto ;
width : 50 % ;
}
@ media screen and ( max-width : 1012px ) {
. secondary-section . g . section . component-wrapper . second-column {
width : 100 % ;
margin-bottom : 32 px ;
}
}
. secondary-section . g . section . component-wrapper . responsive-grid {
display : grid ;
width : 100 % ;
grid-template-columns : repeat ( 1 , 1 fr );
gap : 2 rem ;
}
@ media screen and ( min-width : 64rem ) {
. secondary-section . g . section . component-wrapper . responsive-grid {
grid-template-columns : repeat ( 3 , 1 fr );
}
}
. secondary-section . g . section . component-wrapper . responsive-grid a . card-wrapper {
text-decoration : none ;
transition : none ;
background : none ;
padding : 0 ;
}
. secondary-section . g . section . component-wrapper . responsive-grid . card {
position : relative ;
background-color : #fff none repeat scroll 0 % 0 % ;
padding : 1.5 rem ;
display : flex ;
flex-direction : row ;
-moz- box-align : center ;
align-items : center ;
height : 100 % ;
-moz- box-pack : start ;
justify-content : flex-start ;
box-shadow : rgba ( 0 , 0 , 0 , 0.09 ) 0.3125 rem 0.3125 rem 0 px -0.0625 rem , rgba ( 0 , 0 , 0 , 0.15 ) 0 px 0.25 rem 0.5 rem 0 px ;
transition : all 0.6 s cubic-bezier ( 0.165 , 0.84 , 0.44 , 1 ) 0 s ;
}
. secondary-section . g . section . component-wrapper . responsive-grid . card : hover {
box-shadow : rgba ( 0 , 0 , 0 , 0.2 ) 0.3125 rem 0.3125 rem 0 px -0.0625 rem , rgba ( 0 , 0 , 0 , 0.26 ) 0 px 0.25 rem 0.5 rem 0 px ;
}
@ media screen and ( min-width : 75rem ) {
. secondary-section . g . section . component-wrapper . responsive-grid . card {
padding : 2 rem 2.5 rem ;
}
}
@ media screen and ( min-width : 36rem ) {
. secondary-section . g . section . component-wrapper . responsive-grid . card {
padding : 1 rem 1.5 rem ;
}
}
. secondary-section . g . section . component-wrapper . responsive-grid . card . logo {
margin-right : 0.75 rem ;
width : 1.2 rem ;
min-width : 1.2 rem ;
}
. secondary-section . g . section . component-wrapper . responsive-grid . card . card-content {
display : flex ;
flex : 1 1 0 % ;
flex-direction : column ;
width : 100 % ;
}
. secondary-section . g . section . component-wrapper . responsive-grid . card . card-content h5 {
color : rgb ( 61 , 61 , 61 );
margin : 0 ;
}
. secondary-section . g . section . component-wrapper . responsive-grid . card . card-content p {
margin-top : 0.25 em ;
margin-bottom : 0 ;
color : rgb ( 92 , 92 , 92 );
font-size : 0.65 rem ;
font-weight : 300 ;
line-height : normal ;
}
. secondary-section . g . section . component-wrapper . responsive-grid . card . card-content code {
background : rgba ( 0 , 0 , 0 , 0.05 ) none repeat scroll 0 % 0 % ;
padding : 2 px 6 px ;
border-radius : 4 px ;
}
. component-wrapper span . em {
color : rgb ( 61 , 61 , 61 );
}
. component-wrapper a {
transition : color 125 ms ;
color : rgb ( 61 , 61 , 61 );
background : rgba ( 0 , 0 , 0 , 0.05 ) none repeat scroll 0 % 0 % ;
padding : 2 px 6 px ;
margin : 0 px 1 px ;
border-radius : 4 px ;
display : inline ;
cursor : pointer ;
font-weight : 600 ;
}
. component-wrapper a : hover {
color : var ( -- md - typeset - a - color );
background : var ( -- md - accent - fg - color -- transparent );
}
2025-09-17 22:55:17 +02:00
. before ,
. after {
margin : 0 ;
}
. after figcaption {
background : #fff ;
font-weight : bold ;
border : 1 px solid #c0c0c0 ;
color : #000000 ;
opacity : 0.9 ;
padding : 9 px ;
position : absolute ;
top : 100 % ;
transform : translateY ( -100 % );
line-height : 100 % ;
}
. before figcaption {
background : #000 ;
font-weight : bold ;
border : 1 px solid #c0c0c0 ;
color : #ffffff ;
opacity : 0.9 ;
padding : 9 px ;
position : absolute ;
top : 100 % ;
transform : translateY ( -100 % );
line-height : 100 % ;
}
. before figcaption {
left : 0 px ;
}
. after figcaption {
right : 0 px ;
}
. custom-animated-handle {
transition : transform 0.2 s ;
}
. slider-with-animated-handle : hover . custom-animated-handle {
transform : scale ( 1.2 );
}
. md-typeset img-comparison-slider figure {
margin : initial ;
}
. first-overlay {
color : #000 ;
}
2023-11-02 21:44:14 +01:00
</ style >
<!-- Hero for landing page -->
< div class = "md-container tx-hero" >
< div class = "md-grid md-typeset" >
< div class = "md-main__inner" >
< div >
< h1 > A beautiful and simple UI to manage your WireGuard peers and interfaces</ h1 >
< p > WireGuard Portal is an open source web-based user interface that makes it easy to setup and manage
WireGuard VPN connections. It's built on top of WireGuard's official < span class = "em" > wgctrl</ span > library.</ p >
</ p >
< a
href = "documentation/overview/"
title = "Get Started"
class = "md-button md-button--primary"
>
Get started
< svg width = "11" height = "10" viewBox = "0 0 11 10" fill = "none" style = "margin-left:2px" >< path d = "M1 5.16772H9.5M9.5 5.16772L6.5 1.66772M9.5 5.16772L6.5 8.66772" stroke = "currentColor" stroke-width = "2" stroke-linecap = "round" stroke-linejoin = "round" ></ path ></ svg >
</ a >
</ div >
</ div >
</ div >
</ div >
< div class = "md-container" >
< div class = "tx-hero__image" >
2025-09-17 22:55:17 +02:00
< div >
< img-comparison-slider hover = "hover" >
< figure slot = "first" class = "before" >
< img src = "{{config.site_url}}/assets/images/wgportal_light.png" alt = "Light Mode" />
< figcaption > Light Mode</ figcaption >
</ figure >
< figure slot = "second" class = "after" >
< img src = "{{config.site_url}}/assets/images/wgportal_dark.png" alt = "Dark Mode" />
< figcaption > Dark Mode</ figcaption >
</ figure >
< svg slot = "handle" class = "custom-animated-handle" xmlns = "http://www.w3.org/2000/svg" width = "100" viewBox = "-8 -3 16 6" >
< path stroke = "#fff" d = "M -5 -2 L -7 0 L -5 2 M -5 -2 L -5 2 M 5 -2 L 7 0 L 5 2 M 5 -2 L 5 2" stroke-width = "1" fill = "#fff" vector-effect = "non-scaling-stroke" ></ path >
</ svg >
</ img-comparison-slider >
</ div >
2023-11-02 21:44:14 +01:00
</ div >
</ div >
< div class = "md-container secondary-section" >
< div class = "g" >
<!-- Architecture as building blocks -->
< div class = "section" >
< div class = "component-wrapper" >
< div class = "first-column" >
< h3 > More information about WireGuard</ h3 >
< p >
WireGuard® is an extremely < span class = "em" > simple</ span > yet < span class = "em" > fast</ span > and modern
VPN that utilizes < span class = "em" > state-of-the-art cryptography</ span > .
</ p >
< p >
WireGuard uses state-of-the-art < a href = "https://www.wireguard.com/protocol/" > cryptography</ a > and still
manages to be as easy to configure and deploy as SSH.
A combination of extremely high-speed cryptographic primitives and the fact that WireGuard lives inside
the Linux kernel means that secure networking can be very high-speed.
It is suitable for both small embedded devices like smartphones and fully loaded backbone routers.
</ p >
</ div >
< div class = "second-column" >
< div class = "image-wrapper" >
< img
2024-12-03 19:04:43 +01:00
src = "{{config.site_url}}/assets/images/wg-tool.png"
2023-11-02 21:44:14 +01:00
alt = ""
draggable = "false"
>
</ div >
</ div >
</ div >
< div class = "component-wrapper" style = "display: block;" >
< h4 > Explore official documentation</ h4 >
<!-- Arch as code -->
< div class = "responsive-grid" >
< a class = "card-wrapper" href = "https://www.wireguard.com/" >
< div class = "card" >
< div class = "logo" >
< span class = "twemoji" >
{% include ".icons/octicons/file-code-24.svg" %}
</ span >
</ div >
< div class = "card-content" >
< h5 > Official Website</ h5 >
< p >
If you'd like a general conceptual overview of what WireGuard is about, read onward here.
</ p >
</ div >
</ div >
</ a >
<!-- Networking -->
< a class = "card-wrapper" href = "https://www.wireguard.com/protocol/" >
< div class = "card" >
< div class = "logo" >
< span class = "twemoji" >
{% include ".icons/fontawesome/solid/network-wired.svg" %}
</ span >
</ div >
< div class = "card-content" >
< h5 > Protocol & Cryptography</ h5 >
< p >
WireGuard uses state-of-the-art cryptography, like the Noise protocol framework, Curve25519, ChaCha20, Poly1305, BLAKE2, SipHash24, HKDF, and secure trusted constructions.
</ p >
</ div >
</ div >
</ a >
<!-- Customize -->
< a class = "card-wrapper" href = "https://www.wireguard.com/install/" >
< div class = "card" >
< div class = "logo" >
< span class = "twemoji" >
{% include ".icons/fontawesome/solid/puzzle-piece.svg" %}
</ span >
</ div >
< div class = "card-content" >
< h5 > Client Installation</ h5 >
< p >
You may progress to installation and reading the quickstart instructions on how to use it.
</ p >
</ div >
</ div >
</ a >
</ div >
</ div >
</ div >
</ div >
</ div >
{% endblock %}
<!-- Content -->
{% block content %}{% endblock %}
<!-- Application footer -->
{% block footer %}
{{ super() }}
{% endblock %}