diff --git a/packages/client/src/pages/welcome.entrance.a.vue b/packages/client/src/pages/welcome.entrance.a.vue
index 652d180771..a1d049166b 100644
--- a/packages/client/src/pages/welcome.entrance.a.vue
+++ b/packages/client/src/pages/welcome.entrance.a.vue
@@ -24,6 +24,9 @@
 				@swiper="setSwiperRef"
 				@slide-change="onSlideChange"
 			>
+				<swiper-slide v-slot="{ isActive }">
+					<XKanban v-if="isActive"/>
+				</swiper-slide>
 				<swiper-slide v-slot="{ isActive }">
 					<MkSpacer :content-max="800" v-if="isActive">
 						<XNotes :pagination="paginationForLocal" />
@@ -110,9 +113,10 @@
 </template>
 
 <script lang="ts" setup>
-import { computed, watch, onMounted } from "vue";
+import { computed, watch, onMounted, provide } from "vue";
 import * as os from "@/os";
 import { Swiper, SwiperSlide } from "swiper/vue";
+import XKanban from "@/ui/visitor/kanban.vue";
 import XNotes from "@/components/MkNotes.vue";
 import XUsers from "./explore.users.vue";
 import XChannelList from "@/components/MkChannelList.vue";
@@ -127,7 +131,17 @@ import { DetailedInstanceMetadata } from "calckey-js/built/entities";
 import "swiper/scss";
 import "swiper/scss/virtual";
 
+const DESKTOP_THRESHOLD = 1100;
+let isDesktop = $ref(window.innerWidth >= DESKTOP_THRESHOLD);
+matchMedia(`(min-width: ${DESKTOP_THRESHOLD - 1}px)`).onchange = (mql) => {
+	isDesktop = mql.matches;
+	syncSlide(isDesktop ? 1 : 0);
+};
+
+provide("shouldOmitHeaderTitle", true);
+
 const tabs = [
+	"home",
 	"local",
 	"remote",
 	"channels",
@@ -141,6 +155,11 @@ watch($$(tab), () => syncSlide(tabs.indexOf(tab)));
 const headerActions = $computed(() => []);
 
 const headerTabs = $computed(() => [
+	!isDesktop ? {
+		key: "home",
+		icon: "ph-house ph-bold ph-lg",
+		title: i18n.ts.home,
+	} : [],
 	{
 		key: "local",
 		icon: "ph-lightning ph-bold ph-lg",
@@ -196,7 +215,7 @@ function syncSlide(index) {
 }
 
 onMounted(() => {
-	syncSlide(tabs.indexOf(swiperRef.activeIndex));
+	syncSlide(isDesktop ? 1 : 0);
 });
 
 let meta = $ref<DetailedInstanceMetadata>();
@@ -215,7 +234,6 @@ const paginationForLocal = {
 		days: 14,
 	},
 };
-
 const paginationForRemote = {
 	endpoint: "notes/featured" as const,
 	limit: 20,
diff --git a/packages/client/src/ui/universal.vue b/packages/client/src/ui/universal.vue
index 7f5d0583c6..23bc0022f3 100644
--- a/packages/client/src/ui/universal.vue
+++ b/packages/client/src/ui/universal.vue
@@ -4,7 +4,7 @@
 		:class="{ wallpaper, isMobile, centered: ui === 'classic' }"
 	>
 		<XSidebar v-if="!isMobile && $i" />
-		<XKanban class="kanban" full v-if="!$i" />
+		<XKanban sticky v-if="isDesktop" />
 
 		<MkStickyContainer class="contents">
 			<template #header
@@ -196,7 +196,7 @@ const DESKTOP_THRESHOLD = 1100;
 const MOBILE_THRESHOLD = 500;
 
 // デスクトップでウィンドウを狭くしたときモバイルUIが表示されて欲しいことはあるので deviceKind === 'desktop' の判定は行わない
-const isDesktop = ref(window.innerWidth >= DESKTOP_THRESHOLD);
+let isDesktop = $ref(window.innerWidth >= DESKTOP_THRESHOLD);
 const isMobile = ref(
 	deviceKind === "smartphone" || window.innerWidth <= MOBILE_THRESHOLD
 );
@@ -334,15 +334,9 @@ async function startGroup(): void {
 	mainRouter.push(`/my/messaging/group/${group.id}`);
 }
 
-onMounted(() => {
-	if (!isDesktop.value) {
-		matchMedia(`(min-width: ${DESKTOP_THRESHOLD - 1}px)`).onchange = (
-			mql
-		) => {
-			if (mql.matches) isDesktop.value = true;
-		};
-	}
-});
+matchMedia(`(min-width: ${DESKTOP_THRESHOLD - 1}px)`).onchange = (mql) => {
+	isDesktop = mql.matches;
+};
 
 const onContextmenu = (ev: MouseEvent) => {
 	const isLink = (el: HTMLElement) => {
diff --git a/packages/client/src/ui/visitor/kanban.vue b/packages/client/src/ui/visitor/kanban.vue
index f7460bbfd7..a515a5a63c 100644
--- a/packages/client/src/ui/visitor/kanban.vue
+++ b/packages/client/src/ui/visitor/kanban.vue
@@ -1,21 +1,32 @@
 <template>
-	<div class="instance-info-container" :class="expanded">
+	<div class="instance-info-container"
+		:class="{ sticky }"
+	>
 		<header
 			id="instance-info"
+			v-on:scroll.passive="onScroll"
 		>
-			<div class="ticker" v-if="!expanded">
+			<!-- <div class="ticker" v-if="!expanded">
 				<img 
 					class="logo"
 					:src="meta.logoImageUrl"
 				/>
-				<h1>
-					<MkA
-						to="/" class="link"
-					>{{ instanceName }}</MkA>
-				</h1>
-			</div>
+				<div>
+					<h1>
+						<MkA
+							to="/" class="link"
+						>{{ instanceName }}</MkA>
+					</h1>
+					<p>{{ meta.description || i18n.ts.introMisskey }}</p>
+				</div>
+				<MkButton
+					primary
+					rounded
+					@click.stop="expanded = true"
+				>{{ i18n.ts.instanceInfo }}</MkButton>
+			</div> -->
 			<img class="banner" :src="meta.backgroundImageUrl" />
-			<div class="content" v-if="expanded">
+			<div class="content">
 				<div class="header">
 					<img 
 						class="logo"
@@ -183,14 +194,15 @@ import XSignupDialog from "@/components/MkSignupDialog.vue";
 import MkKeyValue from "@/components/MkKeyValue.vue";
 import MkMention from "@/components/MkMention.vue";
 
-let expanded = $ref(false);
+// let expanded = $ref(window.innerWidth >= 1000);
 
-matchMedia("(max-width: 1000px)").onchange = (mql) => {
-	console.log("ran");
-	expanded = !mql.matches;
-};
+// matchMedia("(max-width: 1000px)").onchange = (mql) => {
+// 	expanded = !mql.matches;
+// };
 
-expanded = true;
+defineProps<{
+	sticky?: boolean;
+}>();
 
 let meta = $ref<DetailedInstanceMetadata>();
 
@@ -234,8 +246,131 @@ function signup() {
 function showMenu(ev) {
 	openHelpMenu_(ev);
 }
+function onScroll(ev) {
+	if (ev.target.scrollTop == 0) {
+		expanded = false;
+	}
+}
 </script>
 
 <style lang="scss" scoped>
-
+.instance-info-container {
+	&.sticky {
+		position: sticky;
+		top: 0;
+		max-height: 100vh;
+		overflow: hidden auto;	
+		min-width: 400px;
+		width: 450px;
+	}
+	margin-left: -1px;
+	border-right: 1px solid var(--divider);
+	box-shadow: 0 0 48px -24px rgba(0,0,0,0.1);
+	z-index: 9000;
+}
+#instance-info {
+	display: flex;
+	flex-direction: column;
+	height: 100%;
+	background: var(--accent);
+	transition: transform .4s cubic-bezier(.5,0,0,1);
+	.banner {
+		position: sticky;
+		top: 0;
+		width: calc(100% + 2px);
+		margin-inline: -1px;
+		min-height: 250px;
+		max-height: 250px;
+		object-fit: cover;
+		object-position: center;
+		mask: linear-gradient(to bottom, black, calc(100% - 50px), transparent);
+		transition: min-height .4s, max-height .4s, filter .7s;
+	}
+	> .content {
+		--margin: 32px;
+		--radius: 16px;
+		display: flow-root;
+		position: relative;
+		z-index: 2;
+		background: var(--bg);
+		border-radius: var(--radius) var(--radius) 0 0;
+		margin-top: calc(0px - var(--radius));
+		padding: 0 var(--margin);
+		text-align: center;
+		flex-grow: 1;
+		max-width: 600px;
+		margin-inline: auto;
+		width: 100%;
+		box-sizing: border-box;
+		
+		> .header {
+			position: relative;
+			margin-top: -50px;
+			&::before {
+				content: "";
+				position: absolute;
+				inset: -5px calc(0px - var(--margin));
+				bottom: -100px;
+				backdrop-filter: blur(60px);
+				filter: brightness(1.2);
+				pointer-events: none;
+				z-index: -1;
+				clip-path: inset(55px 0 0 0 round var(--radius));
+				mask: linear-gradient(transparent 55px, #000 50px, transparent);
+				-webkit-mask: linear-gradient(transparent 55px, #000 50px, transparent);
+			}
+			> .logo {
+				height: 90px;
+				min-width: 90px;
+				border-radius: var(--radius);
+				margin-top: -5px;
+				transition: transform .4s cubic-bezier(0.5,0,0,1);
+			}
+			> h1 {
+				margin-block: .7em;
+				font-size: 1.5em;
+				color: var(--fgHighlighted)
+			}
+		}
+		.menu {
+			position: absolute;
+			top: 10px;
+			right: 10px;
+			width: 42px;
+			height: 42px;
+			border-radius: 100px;
+			background: var(--buttonBg)
+		}
+		.about {
+			position: relative;
+			font-size: 1.05em;
+			.desc {
+				display: block;
+			}
+			.collapsed {
+				position: relative;
+				max-height: calc(9em + 50px);
+				mask: linear-gradient(black calc(100% - 64px), transparent);
+				-webkit-mask: linear-gradient(
+					black calc(100% - 64px),
+					transparent
+				);
+			}
+		}
+		.announcements {
+			text-align: initial;
+		}
+		> :not(.header) {
+			max-width: 600px;
+			margin-inline: auto;
+		}
+	}
+}
+section {
+	margin-top: 2em;
+}
+._formLinksGrid {
+	grid-template-columns: repeat(2,minmax(150px,1fr));
+	text-align: initial;
+}
 </style>