feat: add welcome message for Linear Mode (#8562)

## Summary

Adds a welcome/onboarding message for App Mode (Linear Mode) that
displays when no workflow output is selected, targeting first-time
users.


| Before | After |
|
---------------------------------------------------------------------------------------------------------------------------------------------
|
---------------------------------------------------------------------------------------------------------------------------------------------
|
| <img width="1914" height="1084" alt="Screenshot from 2026-02-02
20-47-30"
src="https://github.com/user-attachments/assets/f3693422-b6ee-496a-a354-d9cede501330"
/> | <img width="1919" height="1085" alt="Screenshot from 2026-02-02
21-32-20"
src="https://github.com/user-attachments/assets/dbfda4d0-251c-4099-ad36-3d7c0220d264"
/> |


## Changes

- **LinearWelcome.vue**: New component with 4 sections explaining App
Mode interface, sharing workflows, and widget control
- **LinearPreview.vue**: Replace dimmed logo fallback with LinearWelcome
component
- **i18n**: Add `linearMode.welcome.*` translation keys

## Review Focus

- Copy targets users who have never used ComfyUI—assumes no knowledge of
nodes/graphs
- Component uses semantic Tailwind classes from design system

Fixes COM-14274

┆Issue is synchronized with this [Notion
page](https://www.notion.so/PR-8562-feat-add-welcome-message-for-Linear-Mode-2fc6d73d365081b2b736f211152e1cce)
by [Unito](https://www.unito.io)


<!-- This is an auto-generated comment: release notes by coderabbit.ai
-->

## Summary by CodeRabbit

* **New Features**
* Added a comprehensive welcome screen in App Mode that introduces users
to the simplified interface hiding node graphs, explains the layout
structure with outputs and controls, provides instructions for sharing
workflows as simple tools, and guides users on customizing which
settings are visible through widget promotion.

<!-- end of auto-generated comment: release notes by coderabbit.ai -->
This commit is contained in:
Christian Byrne
2026-02-02 21:44:30 -08:00
committed by GitHub
parent 5847071bc1
commit ae7728cd91
3 changed files with 39 additions and 6 deletions

View File

@@ -2760,7 +2760,14 @@
"runCount": "Run count:",
"rerun": "Rerun",
"reuseParameters": "Reuse Parameters",
"downloadAll": "Download All"
"downloadAll": "Download All",
"welcome": {
"title": "Welcome to App Mode",
"intro": "A simplified view that hides the node graph so you can focus on creating.",
"layout": "On the left, you'll see your generated images, videos, and outputs. On the right, just the controls you need. Everything complex stays out of sight.",
"sharing": "Sharing is easy: create your workflow, open App Mode, right-click the tab, and export. When others open your file, it launches straight into this clean view. You can share powerful workflows as simple tools without anyone needing to understand node graphs.",
"widget": "If you want to control which settings appear, convert your top-level nodes into a subgraph, then use widget promotion in the toolbox above it to choose what's exposed."
}
},
"missingNodes": {
"cloud": {

View File

@@ -11,6 +11,7 @@ import type { AssetItem } from '@/platform/assets/schemas/assetSchema'
import { useWorkflowStore } from '@/platform/workflow/management/stores/workflowStore'
import { extractWorkflowFromAsset } from '@/platform/workflow/utils/workflowExtractionUtil'
import ImagePreview from '@/renderer/extensions/linearMode/ImagePreview.vue'
import LinearWelcome from '@/renderer/extensions/linearMode/LinearWelcome.vue'
// Lazy-loaded to avoid pulling THREE.js into the main bundle
const Preview3d = () => import('@/renderer/extensions/linearMode/Preview3d.vue')
import VideoPreview from '@/renderer/extensions/linearMode/VideoPreview.vue'
@@ -177,9 +178,5 @@ async function rerun(e: Event) {
v-else-if="getMediaType(selectedOutput) === '3d'"
:model-url="selectedOutput!.url"
/>
<img
v-else
class="pointer-events-none flex-1 max-h-full md:contain-size brightness-50 opacity-10"
src="/assets/images/comfy-logo-mono.svg"
/>
<LinearWelcome v-else />
</template>

View File

@@ -0,0 +1,29 @@
<script setup lang="ts">
import { t } from '@/i18n'
</script>
<template>
<div
role="article"
data-testid="linear-welcome"
class="flex flex-col items-center justify-center h-full gap-6 p-8 max-w-lg mx-auto text-center"
>
<div class="flex flex-col gap-2">
<h2 class="text-xl font-semibold text-base-foreground">
{{ t('linearMode.welcome.title')
}}<sup class="ml-1 text-xs font-normal text-muted-foreground">{{
t('g.experimental')
}}</sup>
</h2>
<p class="text-base text-muted-foreground">
{{ t('linearMode.welcome.intro') }}
</p>
</div>
<div class="flex flex-col gap-3 text-xs text-muted-foreground/70 max-w-md">
<p>{{ t('linearMode.welcome.layout') }}</p>
<p>{{ t('linearMode.welcome.sharing') }}</p>
<p>{{ t('linearMode.welcome.widget') }}</p>
</div>
</div>
</template>