feat: improve space UX (#5549)
* fix: scroll bar hover color * chore: replace board icon * chore: remove close button in upgrade menu * chore: add translation * feat: switch to the next space by shortcut * chore: replace space lock icon * chore: remove arrow icon in change icon button * feat: only show other favorites header if the other two is empty * fix: create new page in current space * feat: create a new page in a newly created space by default * chore: update translations * feat: open the first page after switching space by default * chore: replace board icon * fix: open the first page(non-space) after switching workspace * chore: revert more icon * chore: revert editor version
@ -1,7 +1,7 @@
|
|||||||
import 'package:appflowy/generated/flowy_svgs.g.dart';
|
import 'package:appflowy/generated/flowy_svgs.g.dart';
|
||||||
import 'package:appflowy/generated/locale_keys.g.dart';
|
import 'package:appflowy/generated/locale_keys.g.dart';
|
||||||
import 'package:appflowy/mobile/presentation/bottom_sheet/bottom_sheet.dart';
|
import 'package:appflowy/mobile/presentation/bottom_sheet/bottom_sheet.dart';
|
||||||
import 'package:appflowy/mobile/presentation/home/shared/mobile_view_card.dart';
|
import 'package:appflowy/mobile/presentation/home/shared/mobile_page_card.dart';
|
||||||
import 'package:appflowy/mobile/presentation/page_item/mobile_slide_action_button.dart';
|
import 'package:appflowy/mobile/presentation/page_item/mobile_slide_action_button.dart';
|
||||||
import 'package:appflowy/workspace/application/favorite/favorite_bloc.dart';
|
import 'package:appflowy/workspace/application/favorite/favorite_bloc.dart';
|
||||||
import 'package:appflowy/workspace/application/recent/recent_views_bloc.dart';
|
import 'package:appflowy/workspace/application/recent/recent_views_bloc.dart';
|
||||||
@ -23,7 +23,7 @@ enum MobilePaneActionType {
|
|||||||
|
|
||||||
MobileSlideActionButton actionButton(
|
MobileSlideActionButton actionButton(
|
||||||
BuildContext context, {
|
BuildContext context, {
|
||||||
MobileViewCardType? cardType,
|
MobilePageCardType? cardType,
|
||||||
FolderSpaceType? spaceType,
|
FolderSpaceType? spaceType,
|
||||||
}) {
|
}) {
|
||||||
switch (this) {
|
switch (this) {
|
||||||
@ -133,13 +133,13 @@ enum MobilePaneActionType {
|
|||||||
|
|
||||||
List<MobileViewItemBottomSheetBodyAction> _buildActions(
|
List<MobileViewItemBottomSheetBodyAction> _buildActions(
|
||||||
ViewPB view, {
|
ViewPB view, {
|
||||||
MobileViewCardType? cardType,
|
MobilePageCardType? cardType,
|
||||||
}) {
|
}) {
|
||||||
final isFavorite = view.isFavorite;
|
final isFavorite = view.isFavorite;
|
||||||
|
|
||||||
if (cardType != null) {
|
if (cardType != null) {
|
||||||
switch (cardType) {
|
switch (cardType) {
|
||||||
case MobileViewCardType.recent:
|
case MobilePageCardType.recent:
|
||||||
return [
|
return [
|
||||||
isFavorite
|
isFavorite
|
||||||
? MobileViewItemBottomSheetBodyAction.removeFromFavorites
|
? MobileViewItemBottomSheetBodyAction.removeFromFavorites
|
||||||
@ -150,7 +150,7 @@ enum MobilePaneActionType {
|
|||||||
MobileViewItemBottomSheetBodyAction.divider,
|
MobileViewItemBottomSheetBodyAction.divider,
|
||||||
MobileViewItemBottomSheetBodyAction.removeFromRecent,
|
MobileViewItemBottomSheetBodyAction.removeFromRecent,
|
||||||
];
|
];
|
||||||
case MobileViewCardType.favorite:
|
case MobilePageCardType.favorite:
|
||||||
return [
|
return [
|
||||||
isFavorite
|
isFavorite
|
||||||
? MobileViewItemBottomSheetBodyAction.removeFromFavorites
|
? MobileViewItemBottomSheetBodyAction.removeFromFavorites
|
||||||
@ -179,7 +179,7 @@ ActionPane buildEndActionPane(
|
|||||||
BuildContext context,
|
BuildContext context,
|
||||||
List<MobilePaneActionType> actions, {
|
List<MobilePaneActionType> actions, {
|
||||||
bool needSpace = true,
|
bool needSpace = true,
|
||||||
MobileViewCardType? cardType,
|
MobilePageCardType? cardType,
|
||||||
FolderSpaceType? spaceType,
|
FolderSpaceType? spaceType,
|
||||||
}) {
|
}) {
|
||||||
return ActionPane(
|
return ActionPane(
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
import 'package:appflowy/mobile/application/mobile_router.dart';
|
import 'package:appflowy/mobile/application/mobile_router.dart';
|
||||||
import 'package:appflowy/mobile/presentation/home/shared/empty_placeholder.dart';
|
import 'package:appflowy/mobile/presentation/home/shared/empty_placeholder.dart';
|
||||||
import 'package:appflowy/mobile/presentation/home/shared/mobile_view_card.dart';
|
import 'package:appflowy/mobile/presentation/home/shared/mobile_page_card.dart';
|
||||||
import 'package:appflowy/util/theme_extension.dart';
|
import 'package:appflowy/util/theme_extension.dart';
|
||||||
import 'package:appflowy/workspace/application/favorite/favorite_bloc.dart';
|
import 'package:appflowy/workspace/application/favorite/favorite_bloc.dart';
|
||||||
import 'package:appflowy/workspace/application/menu/sidebar_sections_bloc.dart';
|
import 'package:appflowy/workspace/application/menu/sidebar_sections_bloc.dart';
|
||||||
@ -69,7 +69,7 @@ class _MobileFavoriteSpaceState extends State<MobileFavoriteSpace>
|
|||||||
|
|
||||||
if (favoriteState.views.isEmpty) {
|
if (favoriteState.views.isEmpty) {
|
||||||
return const EmptySpacePlaceholder(
|
return const EmptySpacePlaceholder(
|
||||||
type: MobileViewCardType.favorite,
|
type: MobilePageCardType.favorite,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -117,11 +117,11 @@ class _FavoriteViews extends StatelessWidget {
|
|||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
child: MobileViewCard(
|
child: MobileViewPage(
|
||||||
key: ValueKey(view.item.id),
|
key: ValueKey(view.item.id),
|
||||||
view: view.item,
|
view: view.item,
|
||||||
timestamp: view.timestamp,
|
timestamp: view.timestamp,
|
||||||
type: MobileViewCardType.favorite,
|
type: MobilePageCardType.favorite,
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
|
@ -42,8 +42,8 @@ class MobileFolders extends StatelessWidget {
|
|||||||
create: (_) => FavoriteBloc()..add(const FavoriteEvent.initial()),
|
create: (_) => FavoriteBloc()..add(const FavoriteEvent.initial()),
|
||||||
),
|
),
|
||||||
BlocProvider(
|
BlocProvider(
|
||||||
create: (_) =>
|
create: (_) => SpaceBloc()
|
||||||
SpaceBloc()..add(SpaceEvent.initial(user, workspaceId)),
|
..add(SpaceEvent.initial(user, workspaceId, openFirstPage: false)),
|
||||||
),
|
),
|
||||||
],
|
],
|
||||||
child: BlocListener<UserWorkspaceBloc, UserWorkspaceState>(
|
child: BlocListener<UserWorkspaceBloc, UserWorkspaceState>(
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
import 'package:appflowy/mobile/presentation/home/shared/empty_placeholder.dart';
|
import 'package:appflowy/mobile/presentation/home/shared/empty_placeholder.dart';
|
||||||
import 'package:appflowy/mobile/presentation/home/shared/mobile_view_card.dart';
|
import 'package:appflowy/mobile/presentation/home/shared/mobile_page_card.dart';
|
||||||
import 'package:appflowy/util/theme_extension.dart';
|
import 'package:appflowy/util/theme_extension.dart';
|
||||||
import 'package:appflowy/workspace/application/recent/prelude.dart';
|
import 'package:appflowy/workspace/application/recent/prelude.dart';
|
||||||
import 'package:appflowy/workspace/presentation/home/home_sizes.dart';
|
import 'package:appflowy/workspace/presentation/home/home_sizes.dart';
|
||||||
@ -37,7 +37,7 @@ class _MobileRecentSpaceState extends State<MobileRecentSpace>
|
|||||||
|
|
||||||
if (recentViews.isEmpty) {
|
if (recentViews.isEmpty) {
|
||||||
return const Center(
|
return const Center(
|
||||||
child: EmptySpacePlaceholder(type: MobileViewCardType.recent),
|
child: EmptySpacePlaceholder(type: MobilePageCardType.recent),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -89,11 +89,11 @@ class _RecentViews extends StatelessWidget {
|
|||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
child: MobileViewCard(
|
child: MobileViewPage(
|
||||||
key: ValueKey(sectionView.item.id),
|
key: ValueKey(sectionView.item.id),
|
||||||
view: sectionView.item,
|
view: sectionView.item,
|
||||||
timestamp: sectionView.timestamp,
|
timestamp: sectionView.timestamp,
|
||||||
type: MobileViewCardType.recent,
|
type: MobilePageCardType.recent,
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
import 'package:appflowy/generated/flowy_svgs.g.dart';
|
import 'package:appflowy/generated/flowy_svgs.g.dart';
|
||||||
import 'package:appflowy/generated/locale_keys.g.dart';
|
import 'package:appflowy/generated/locale_keys.g.dart';
|
||||||
import 'package:appflowy/mobile/presentation/home/shared/mobile_view_card.dart';
|
import 'package:appflowy/mobile/presentation/home/shared/mobile_page_card.dart';
|
||||||
import 'package:easy_localization/easy_localization.dart';
|
import 'package:easy_localization/easy_localization.dart';
|
||||||
import 'package:flowy_infra_ui/flowy_infra_ui.dart';
|
import 'package:flowy_infra_ui/flowy_infra_ui.dart';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
@ -8,7 +8,7 @@ import 'package:flutter/material.dart';
|
|||||||
class EmptySpacePlaceholder extends StatelessWidget {
|
class EmptySpacePlaceholder extends StatelessWidget {
|
||||||
const EmptySpacePlaceholder({super.key, required this.type});
|
const EmptySpacePlaceholder({super.key, required this.type});
|
||||||
|
|
||||||
final MobileViewCardType type;
|
final MobilePageCardType type;
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
@ -42,14 +42,14 @@ class EmptySpacePlaceholder extends StatelessWidget {
|
|||||||
}
|
}
|
||||||
|
|
||||||
String get _emptyPageText => switch (type) {
|
String get _emptyPageText => switch (type) {
|
||||||
MobileViewCardType.recent => LocaleKeys.sideBar_emptyRecent.tr(),
|
MobilePageCardType.recent => LocaleKeys.sideBar_emptyRecent.tr(),
|
||||||
MobileViewCardType.favorite => LocaleKeys.sideBar_emptyFavorite.tr(),
|
MobilePageCardType.favorite => LocaleKeys.sideBar_emptyFavorite.tr(),
|
||||||
};
|
};
|
||||||
|
|
||||||
String get _emptyPageSubText => switch (type) {
|
String get _emptyPageSubText => switch (type) {
|
||||||
MobileViewCardType.recent =>
|
MobilePageCardType.recent =>
|
||||||
LocaleKeys.sideBar_emptyRecentDescription.tr(),
|
LocaleKeys.sideBar_emptyRecentDescription.tr(),
|
||||||
MobileViewCardType.favorite =>
|
MobilePageCardType.favorite =>
|
||||||
LocaleKeys.sideBar_emptyFavoriteDescription.tr(),
|
LocaleKeys.sideBar_emptyFavoriteDescription.tr(),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
@ -29,18 +29,18 @@ import 'package:provider/provider.dart';
|
|||||||
import 'package:string_validator/string_validator.dart';
|
import 'package:string_validator/string_validator.dart';
|
||||||
import 'package:time/time.dart';
|
import 'package:time/time.dart';
|
||||||
|
|
||||||
enum MobileViewCardType {
|
enum MobilePageCardType {
|
||||||
recent,
|
recent,
|
||||||
favorite;
|
favorite;
|
||||||
|
|
||||||
String get lastOperationHintText => switch (this) {
|
String get lastOperationHintText => switch (this) {
|
||||||
MobileViewCardType.recent => LocaleKeys.sideBar_lastViewed.tr(),
|
MobilePageCardType.recent => LocaleKeys.sideBar_lastViewed.tr(),
|
||||||
MobileViewCardType.favorite => LocaleKeys.sideBar_favoriteAt.tr(),
|
MobilePageCardType.favorite => LocaleKeys.sideBar_favoriteAt.tr(),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
class MobileViewCard extends StatelessWidget {
|
class MobileViewPage extends StatelessWidget {
|
||||||
const MobileViewCard({
|
const MobileViewPage({
|
||||||
super.key,
|
super.key,
|
||||||
required this.view,
|
required this.view,
|
||||||
this.timestamp,
|
this.timestamp,
|
||||||
@ -49,7 +49,7 @@ class MobileViewCard extends StatelessWidget {
|
|||||||
|
|
||||||
final ViewPB view;
|
final ViewPB view;
|
||||||
final Int64? timestamp;
|
final Int64? timestamp;
|
||||||
final MobileViewCardType type;
|
final MobilePageCardType type;
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
@ -42,10 +42,6 @@ class _MobileSpaceState extends State<MobileSpace> {
|
|||||||
SpaceEvent.createPage(
|
SpaceEvent.createPage(
|
||||||
name: LocaleKeys.menuAppHeader_defaultNewPageName.tr(),
|
name: LocaleKeys.menuAppHeader_defaultNewPageName.tr(),
|
||||||
index: 0,
|
index: 0,
|
||||||
viewSection: currentSpace.spacePermission ==
|
|
||||||
SpacePermission.publicToAll
|
|
||||||
? ViewSectionPB.Public
|
|
||||||
: ViewSectionPB.Private,
|
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
context.read<SpaceBloc>().add(
|
context.read<SpaceBloc>().add(
|
||||||
|
@ -58,8 +58,6 @@ class EditorStyleCustomizer {
|
|||||||
DefaultAppearanceSettings.getDefaultSelectionColor(context),
|
DefaultAppearanceSettings.getDefaultSelectionColor(context),
|
||||||
defaultTextDirection: appearance.defaultTextDirection,
|
defaultTextDirection: appearance.defaultTextDirection,
|
||||||
textStyleConfiguration: TextStyleConfiguration(
|
textStyleConfiguration: TextStyleConfiguration(
|
||||||
// applyHeightToFirstAscent: true,
|
|
||||||
// applyHeightToLastDescent: true,
|
|
||||||
text: baseTextStyle(fontFamily).copyWith(
|
text: baseTextStyle(fontFamily).copyWith(
|
||||||
fontSize: fontSize,
|
fontSize: fontSize,
|
||||||
color: afThemeExtension.onBackground,
|
color: afThemeExtension.onBackground,
|
||||||
|
@ -76,7 +76,7 @@ class DesktopAppearance extends BaseAppearance {
|
|||||||
scrollbarTheme: ScrollbarThemeData(
|
scrollbarTheme: ScrollbarThemeData(
|
||||||
thumbColor: WidgetStateProperty.resolveWith((states) {
|
thumbColor: WidgetStateProperty.resolveWith((states) {
|
||||||
if (states.any(scrollbarInteractiveStates.contains)) {
|
if (states.any(scrollbarInteractiveStates.contains)) {
|
||||||
return theme.shader7;
|
return theme.shader3;
|
||||||
}
|
}
|
||||||
return theme.shader5;
|
return theme.shader5;
|
||||||
}),
|
}),
|
||||||
@ -102,6 +102,7 @@ class DesktopAppearance extends BaseAppearance {
|
|||||||
indicatorColor: theme.main1,
|
indicatorColor: theme.main1,
|
||||||
cardColor: theme.input,
|
cardColor: theme.input,
|
||||||
colorScheme: colorScheme,
|
colorScheme: colorScheme,
|
||||||
|
|
||||||
extensions: [
|
extensions: [
|
||||||
AFThemeExtension(
|
AFThemeExtension(
|
||||||
warning: theme.yellow,
|
warning: theme.yellow,
|
||||||
|
@ -3,6 +3,7 @@ import 'dart:convert';
|
|||||||
|
|
||||||
import 'package:appflowy/core/config/kv.dart';
|
import 'package:appflowy/core/config/kv.dart';
|
||||||
import 'package:appflowy/core/config/kv_keys.dart';
|
import 'package:appflowy/core/config/kv_keys.dart';
|
||||||
|
import 'package:appflowy/generated/locale_keys.g.dart';
|
||||||
import 'package:appflowy/startup/startup.dart';
|
import 'package:appflowy/startup/startup.dart';
|
||||||
import 'package:appflowy/user/application/user_service.dart';
|
import 'package:appflowy/user/application/user_service.dart';
|
||||||
import 'package:appflowy/workspace/application/view/view_ext.dart';
|
import 'package:appflowy/workspace/application/view/view_ext.dart';
|
||||||
@ -16,6 +17,7 @@ import 'package:appflowy_backend/protobuf/flowy-folder/view.pb.dart';
|
|||||||
import 'package:appflowy_backend/protobuf/flowy-user/protobuf.dart';
|
import 'package:appflowy_backend/protobuf/flowy-user/protobuf.dart';
|
||||||
import 'package:appflowy_result/appflowy_result.dart';
|
import 'package:appflowy_result/appflowy_result.dart';
|
||||||
import 'package:collection/collection.dart';
|
import 'package:collection/collection.dart';
|
||||||
|
import 'package:easy_localization/easy_localization.dart';
|
||||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||||
import 'package:freezed_annotation/freezed_annotation.dart';
|
import 'package:freezed_annotation/freezed_annotation.dart';
|
||||||
import 'package:protobuf/protobuf.dart';
|
import 'package:protobuf/protobuf.dart';
|
||||||
@ -60,7 +62,7 @@ class SpaceBloc extends Bloc<SpaceEvent, SpaceState> {
|
|||||||
on<SpaceEvent>(
|
on<SpaceEvent>(
|
||||||
(event, emit) async {
|
(event, emit) async {
|
||||||
await event.when(
|
await event.when(
|
||||||
initial: (userProfile, workspaceId) async {
|
initial: (userProfile, workspaceId, openFirstPage) async {
|
||||||
_initial(userProfile, workspaceId);
|
_initial(userProfile, workspaceId);
|
||||||
|
|
||||||
final (spaces, publicViews, privateViews) = await _getSpaces();
|
final (spaces, publicViews, privateViews) = await _getSpaces();
|
||||||
@ -84,8 +86,20 @@ class SpaceBloc extends Bloc<SpaceEvent, SpaceState> {
|
|||||||
if (shouldShowUpgradeDialog) {
|
if (shouldShowUpgradeDialog) {
|
||||||
add(const SpaceEvent.migrate());
|
add(const SpaceEvent.migrate());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (openFirstPage) {
|
||||||
|
if (currentSpace != null) {
|
||||||
|
add(SpaceEvent.open(currentSpace));
|
||||||
|
}
|
||||||
|
}
|
||||||
},
|
},
|
||||||
create: (name, icon, iconColor, permission) async {
|
create: (
|
||||||
|
name,
|
||||||
|
icon,
|
||||||
|
iconColor,
|
||||||
|
permission,
|
||||||
|
createNewPageByDefault,
|
||||||
|
) async {
|
||||||
final space = await _createSpace(
|
final space = await _createSpace(
|
||||||
name: name,
|
name: name,
|
||||||
icon: icon,
|
icon: icon,
|
||||||
@ -93,8 +107,22 @@ class SpaceBloc extends Bloc<SpaceEvent, SpaceState> {
|
|||||||
permission: permission,
|
permission: permission,
|
||||||
);
|
);
|
||||||
if (space != null) {
|
if (space != null) {
|
||||||
emit(state.copyWith(spaces: [...state.spaces, space]));
|
emit(
|
||||||
|
state.copyWith(
|
||||||
|
spaces: [...state.spaces, space],
|
||||||
|
currentSpace: space,
|
||||||
|
),
|
||||||
|
);
|
||||||
add(SpaceEvent.open(space));
|
add(SpaceEvent.open(space));
|
||||||
|
|
||||||
|
if (createNewPageByDefault) {
|
||||||
|
add(
|
||||||
|
SpaceEvent.createPage(
|
||||||
|
name: LocaleKeys.menuAppHeader_defaultNewPageName.tr(),
|
||||||
|
index: 0,
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
delete: (space) async {
|
delete: (space) async {
|
||||||
@ -160,12 +188,28 @@ class SpaceBloc extends Bloc<SpaceEvent, SpaceState> {
|
|||||||
await _openSpace(space);
|
await _openSpace(space);
|
||||||
final isExpanded = await _getSpaceExpandStatus(space);
|
final isExpanded = await _getSpaceExpandStatus(space);
|
||||||
emit(state.copyWith(currentSpace: space, isExpanded: isExpanded));
|
emit(state.copyWith(currentSpace: space, isExpanded: isExpanded));
|
||||||
|
|
||||||
|
// open the first page by default
|
||||||
|
if (space.childViews.isNotEmpty) {
|
||||||
|
final firstPage = space.childViews.first;
|
||||||
|
emit(
|
||||||
|
state.copyWith(
|
||||||
|
lastCreatedPage: firstPage,
|
||||||
|
),
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
emit(
|
||||||
|
state.copyWith(
|
||||||
|
lastCreatedPage: ViewPB(),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
},
|
},
|
||||||
expand: (space, isExpanded) async {
|
expand: (space, isExpanded) async {
|
||||||
await _setSpaceExpandStatus(space, isExpanded);
|
await _setSpaceExpandStatus(space, isExpanded);
|
||||||
emit(state.copyWith(isExpanded: isExpanded));
|
emit(state.copyWith(isExpanded: isExpanded));
|
||||||
},
|
},
|
||||||
createPage: (name, section, index) async {
|
createPage: (name, index) async {
|
||||||
final parentViewId = state.currentSpace?.id;
|
final parentViewId = state.currentSpace?.id;
|
||||||
if (parentViewId == null) {
|
if (parentViewId == null) {
|
||||||
return;
|
return;
|
||||||
@ -209,12 +253,33 @@ class SpaceBloc extends Bloc<SpaceEvent, SpaceState> {
|
|||||||
reset: (userProfile, workspaceId) async {
|
reset: (userProfile, workspaceId) async {
|
||||||
_reset(userProfile, workspaceId);
|
_reset(userProfile, workspaceId);
|
||||||
|
|
||||||
add(SpaceEvent.initial(userProfile, workspaceId));
|
add(
|
||||||
|
SpaceEvent.initial(
|
||||||
|
userProfile,
|
||||||
|
workspaceId,
|
||||||
|
openFirstPage: true,
|
||||||
|
),
|
||||||
|
);
|
||||||
},
|
},
|
||||||
migrate: () async {
|
migrate: () async {
|
||||||
final result = await migrate();
|
final result = await migrate();
|
||||||
emit(state.copyWith(shouldShowUpgradeDialog: !result));
|
emit(state.copyWith(shouldShowUpgradeDialog: !result));
|
||||||
},
|
},
|
||||||
|
switchToNextSpace: () async {
|
||||||
|
final spaces = state.spaces;
|
||||||
|
if (spaces.isEmpty) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
final currentSpace = state.currentSpace;
|
||||||
|
if (currentSpace == null) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
final currentIndex = spaces.indexOf(currentSpace);
|
||||||
|
final nextIndex = (currentIndex + 1) % spaces.length;
|
||||||
|
final nextSpace = spaces[nextIndex];
|
||||||
|
add(SpaceEvent.open(nextSpace));
|
||||||
|
},
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
@ -410,7 +475,7 @@ class SpaceBloc extends Bloc<SpaceEvent, SpaceState> {
|
|||||||
// only migrate the public space if there are any public views
|
// only migrate the public space if there are any public views
|
||||||
if (publicViews.isNotEmpty) {
|
if (publicViews.isNotEmpty) {
|
||||||
final publicSpace = await _createSpace(
|
final publicSpace = await _createSpace(
|
||||||
name: 'General',
|
name: 'Shared',
|
||||||
icon: builtInSpaceIcons.first,
|
icon: builtInSpaceIcons.first,
|
||||||
iconColor: builtInSpaceColors.first,
|
iconColor: builtInSpaceColors.first,
|
||||||
permission: SpacePermission.publicToAll,
|
permission: SpacePermission.publicToAll,
|
||||||
@ -487,13 +552,15 @@ class SpaceBloc extends Bloc<SpaceEvent, SpaceState> {
|
|||||||
class SpaceEvent with _$SpaceEvent {
|
class SpaceEvent with _$SpaceEvent {
|
||||||
const factory SpaceEvent.initial(
|
const factory SpaceEvent.initial(
|
||||||
UserProfilePB userProfile,
|
UserProfilePB userProfile,
|
||||||
String workspaceId,
|
String workspaceId, {
|
||||||
) = _Initial;
|
required bool openFirstPage,
|
||||||
|
}) = _Initial;
|
||||||
const factory SpaceEvent.create({
|
const factory SpaceEvent.create({
|
||||||
required String name,
|
required String name,
|
||||||
required String icon,
|
required String icon,
|
||||||
required String iconColor,
|
required String iconColor,
|
||||||
required SpacePermission permission,
|
required SpacePermission permission,
|
||||||
|
required bool createNewPageByDefault,
|
||||||
}) = _Create;
|
}) = _Create;
|
||||||
const factory SpaceEvent.rename(ViewPB space, String name) = _Rename;
|
const factory SpaceEvent.rename(ViewPB space, String name) = _Rename;
|
||||||
const factory SpaceEvent.changeIcon(String icon, String iconColor) =
|
const factory SpaceEvent.changeIcon(String icon, String iconColor) =
|
||||||
@ -508,7 +575,6 @@ class SpaceEvent with _$SpaceEvent {
|
|||||||
const factory SpaceEvent.expand(ViewPB space, bool isExpanded) = _Expand;
|
const factory SpaceEvent.expand(ViewPB space, bool isExpanded) = _Expand;
|
||||||
const factory SpaceEvent.createPage({
|
const factory SpaceEvent.createPage({
|
||||||
required String name,
|
required String name,
|
||||||
required ViewSectionPB viewSection,
|
|
||||||
int? index,
|
int? index,
|
||||||
}) = _CreatePage;
|
}) = _CreatePage;
|
||||||
const factory SpaceEvent.delete(ViewPB? space) = _Delete;
|
const factory SpaceEvent.delete(ViewPB? space) = _Delete;
|
||||||
@ -518,6 +584,7 @@ class SpaceEvent with _$SpaceEvent {
|
|||||||
String workspaceId,
|
String workspaceId,
|
||||||
) = _Reset;
|
) = _Reset;
|
||||||
const factory SpaceEvent.migrate() = _Migrate;
|
const factory SpaceEvent.migrate() = _Migrate;
|
||||||
|
const factory SpaceEvent.switchToNextSpace() = _SwitchToNextSpace;
|
||||||
}
|
}
|
||||||
|
|
||||||
@freezed
|
@freezed
|
||||||
|
@ -1,7 +1,5 @@
|
|||||||
import 'dart:io';
|
import 'dart:io';
|
||||||
|
|
||||||
import 'package:flutter/material.dart';
|
|
||||||
|
|
||||||
import 'package:appflowy/startup/startup.dart';
|
import 'package:appflowy/startup/startup.dart';
|
||||||
import 'package:appflowy/startup/tasks/app_window_size_manager.dart';
|
import 'package:appflowy/startup/tasks/app_window_size_manager.dart';
|
||||||
import 'package:appflowy/workspace/application/home/home_setting_bloc.dart';
|
import 'package:appflowy/workspace/application/home/home_setting_bloc.dart';
|
||||||
@ -11,12 +9,15 @@ import 'package:appflowy/workspace/application/tabs/tabs_bloc.dart';
|
|||||||
import 'package:appflowy/workspace/presentation/home/menu/sidebar/shared/sidebar_setting.dart';
|
import 'package:appflowy/workspace/presentation/home/menu/sidebar/shared/sidebar_setting.dart';
|
||||||
import 'package:appflowy_backend/log.dart';
|
import 'package:appflowy_backend/log.dart';
|
||||||
import 'package:appflowy_backend/protobuf/flowy-user/user_profile.pb.dart';
|
import 'package:appflowy_backend/protobuf/flowy-user/user_profile.pb.dart';
|
||||||
|
import 'package:flutter/material.dart';
|
||||||
import 'package:hotkey_manager/hotkey_manager.dart';
|
import 'package:hotkey_manager/hotkey_manager.dart';
|
||||||
import 'package:provider/provider.dart';
|
import 'package:provider/provider.dart';
|
||||||
import 'package:scaled_app/scaled_app.dart';
|
import 'package:scaled_app/scaled_app.dart';
|
||||||
|
|
||||||
typedef KeyDownHandler = void Function(HotKey hotKey);
|
typedef KeyDownHandler = void Function(HotKey hotKey);
|
||||||
|
|
||||||
|
ValueNotifier<int> switchToTheNextSpace = ValueNotifier(0);
|
||||||
|
|
||||||
/// Helper class that utilizes the global [HotKeyManager] to easily
|
/// Helper class that utilizes the global [HotKeyManager] to easily
|
||||||
/// add a [HotKey] with different handlers.
|
/// add a [HotKey] with different handlers.
|
||||||
///
|
///
|
||||||
@ -163,6 +164,16 @@ class _HomeHotKeysState extends State<HomeHotKeys> {
|
|||||||
keyDownHandler: (_) => _scaleToSize(1),
|
keyDownHandler: (_) => _scaleToSize(1),
|
||||||
),
|
),
|
||||||
|
|
||||||
|
// Switch to the next space
|
||||||
|
HotKeyItem(
|
||||||
|
hotKey: HotKey(
|
||||||
|
KeyCode.keyO,
|
||||||
|
modifiers: [Platform.isMacOS ? KeyModifier.meta : KeyModifier.control],
|
||||||
|
scope: HotKeyScope.inapp,
|
||||||
|
),
|
||||||
|
keyDownHandler: (_) => switchToTheNextSpace.value++,
|
||||||
|
),
|
||||||
|
|
||||||
// Open settings dialog
|
// Open settings dialog
|
||||||
openSettingsHotKey(context, widget.userProfile),
|
openSettingsHotKey(context, widget.userProfile),
|
||||||
];
|
];
|
||||||
|
@ -62,6 +62,21 @@ class FavoriteMenu extends StatelessWidget {
|
|||||||
}
|
}
|
||||||
|
|
||||||
Widget _buildViews(BuildContext context, FavoriteMenuState state) {
|
Widget _buildViews(BuildContext context, FavoriteMenuState state) {
|
||||||
|
final today = _buildGroups(
|
||||||
|
context,
|
||||||
|
state.todayViews,
|
||||||
|
LocaleKeys.sideBar_today.tr(),
|
||||||
|
);
|
||||||
|
final thisWeek = _buildGroups(
|
||||||
|
context,
|
||||||
|
state.thisWeekViews,
|
||||||
|
LocaleKeys.sideBar_thisWeek.tr(),
|
||||||
|
);
|
||||||
|
final others = _buildGroups(
|
||||||
|
context,
|
||||||
|
state.otherViews,
|
||||||
|
LocaleKeys.sideBar_others.tr(),
|
||||||
|
);
|
||||||
return Container(
|
return Container(
|
||||||
width: minWidth - 2 * _kHorizontalPadding,
|
width: minWidth - 2 * _kHorizontalPadding,
|
||||||
constraints: const BoxConstraints(
|
constraints: const BoxConstraints(
|
||||||
@ -72,21 +87,26 @@ class FavoriteMenu extends StatelessWidget {
|
|||||||
mainAxisSize: MainAxisSize.min,
|
mainAxisSize: MainAxisSize.min,
|
||||||
crossAxisAlignment: CrossAxisAlignment.start,
|
crossAxisAlignment: CrossAxisAlignment.start,
|
||||||
children: [
|
children: [
|
||||||
..._buildGroups(
|
if (today.isNotEmpty) ...[
|
||||||
context,
|
...today,
|
||||||
state.todayViews,
|
const VSpace(8),
|
||||||
LocaleKeys.sideBar_today.tr(),
|
const Divider(height: 1),
|
||||||
),
|
const VSpace(8),
|
||||||
..._buildGroups(
|
],
|
||||||
context,
|
if (thisWeek.isNotEmpty) ...[
|
||||||
state.thisWeekViews,
|
...thisWeek,
|
||||||
LocaleKeys.sideBar_thisWeek.tr(),
|
const VSpace(8),
|
||||||
),
|
const Divider(height: 1),
|
||||||
..._buildGroups(
|
const VSpace(8),
|
||||||
context,
|
],
|
||||||
state.otherViews,
|
...others.isNotEmpty && (today.isNotEmpty || thisWeek.isNotEmpty)
|
||||||
LocaleKeys.sideBar_others.tr(),
|
? others
|
||||||
),
|
: _buildGroups(
|
||||||
|
context,
|
||||||
|
state.otherViews,
|
||||||
|
LocaleKeys.sideBar_others.tr(),
|
||||||
|
showHeader: false,
|
||||||
|
),
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
@ -96,23 +116,23 @@ class FavoriteMenu extends StatelessWidget {
|
|||||||
List<Widget> _buildGroups(
|
List<Widget> _buildGroups(
|
||||||
BuildContext context,
|
BuildContext context,
|
||||||
List<ViewPB> views,
|
List<ViewPB> views,
|
||||||
String title,
|
String title, {
|
||||||
) {
|
bool showHeader = true,
|
||||||
|
}) {
|
||||||
return [
|
return [
|
||||||
if (views.isNotEmpty) ...[
|
if (views.isNotEmpty) ...[
|
||||||
SizedBox(
|
if (showHeader)
|
||||||
height: 24,
|
SizedBox(
|
||||||
child: FlowyText(
|
height: 24,
|
||||||
title,
|
child: FlowyText(
|
||||||
fontSize: 12.0,
|
title,
|
||||||
color: Theme.of(context).hintColor,
|
fontSize: 12.0,
|
||||||
|
color: Theme.of(context).hintColor,
|
||||||
|
),
|
||||||
),
|
),
|
||||||
),
|
|
||||||
const VSpace(2),
|
const VSpace(2),
|
||||||
_buildGroupedViews(context, views),
|
_buildGroupedViews(context, views),
|
||||||
const VSpace(8),
|
const VSpace(8),
|
||||||
const Divider(height: 1),
|
|
||||||
const VSpace(8),
|
|
||||||
],
|
],
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
import 'package:appflowy/generated/flowy_svgs.g.dart';
|
import 'package:appflowy/generated/flowy_svgs.g.dart';
|
||||||
import 'package:appflowy/generated/locale_keys.g.dart';
|
import 'package:appflowy/generated/locale_keys.g.dart';
|
||||||
import 'package:appflowy/workspace/application/menu/sidebar_sections_bloc.dart';
|
import 'package:appflowy/workspace/application/menu/sidebar_sections_bloc.dart';
|
||||||
|
import 'package:appflowy/workspace/application/sidebar/space/space_bloc.dart';
|
||||||
import 'package:appflowy/workspace/application/user/user_workspace_bloc.dart';
|
import 'package:appflowy/workspace/application/user/user_workspace_bloc.dart';
|
||||||
import 'package:appflowy/workspace/presentation/home/home_sizes.dart';
|
import 'package:appflowy/workspace/presentation/home/home_sizes.dart';
|
||||||
import 'package:appflowy/workspace/presentation/home/menu/sidebar/shared/rename_view_dialog.dart';
|
import 'package:appflowy/workspace/presentation/home/menu/sidebar/shared/rename_view_dialog.dart';
|
||||||
@ -48,13 +49,23 @@ class SidebarNewPageButton extends StatelessWidget {
|
|||||||
context.read<UserWorkspaceBloc>().state.isCollabWorkspaceOn
|
context.read<UserWorkspaceBloc>().state.isCollabWorkspaceOn
|
||||||
? ViewSectionPB.Private
|
? ViewSectionPB.Private
|
||||||
: ViewSectionPB.Public;
|
: ViewSectionPB.Public;
|
||||||
context.read<SidebarSectionsBloc>().add(
|
final spaceState = context.read<SpaceBloc>().state;
|
||||||
SidebarSectionsEvent.createRootViewInSection(
|
if (spaceState.spaces.isNotEmpty) {
|
||||||
name: viewName,
|
context.read<SpaceBloc>().add(
|
||||||
viewSection: section,
|
SpaceEvent.createPage(
|
||||||
index: 0,
|
name: viewName,
|
||||||
),
|
index: 0,
|
||||||
);
|
),
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
context.read<SidebarSectionsBloc>().add(
|
||||||
|
SidebarSectionsEvent.createRootViewInSection(
|
||||||
|
name: viewName,
|
||||||
|
viewSection: section,
|
||||||
|
index: 0,
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
@ -2,6 +2,7 @@ import 'dart:async';
|
|||||||
|
|
||||||
import 'package:appflowy/generated/flowy_svgs.g.dart';
|
import 'package:appflowy/generated/flowy_svgs.g.dart';
|
||||||
import 'package:appflowy/generated/locale_keys.g.dart';
|
import 'package:appflowy/generated/locale_keys.g.dart';
|
||||||
|
import 'package:appflowy/plugins/blank/blank.dart';
|
||||||
import 'package:appflowy/shared/feature_flags.dart';
|
import 'package:appflowy/shared/feature_flags.dart';
|
||||||
import 'package:appflowy/startup/startup.dart';
|
import 'package:appflowy/startup/startup.dart';
|
||||||
import 'package:appflowy/workspace/application/action_navigation/action_navigation_bloc.dart';
|
import 'package:appflowy/workspace/application/action_navigation/action_navigation_bloc.dart';
|
||||||
@ -116,6 +117,7 @@ class HomeSideBar extends StatelessWidget {
|
|||||||
userProfile,
|
userProfile,
|
||||||
state.currentWorkspace?.workspaceId ??
|
state.currentWorkspace?.workspaceId ??
|
||||||
workspaceSetting.workspaceId,
|
workspaceSetting.workspaceId,
|
||||||
|
openFirstPage: false,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
@ -134,11 +136,23 @@ class HomeSideBar extends StatelessWidget {
|
|||||||
BlocListener<SpaceBloc, SpaceState>(
|
BlocListener<SpaceBloc, SpaceState>(
|
||||||
listenWhen: (p, c) =>
|
listenWhen: (p, c) =>
|
||||||
p.lastCreatedPage?.id != c.lastCreatedPage?.id,
|
p.lastCreatedPage?.id != c.lastCreatedPage?.id,
|
||||||
listener: (context, state) => context.read<TabsBloc>().add(
|
listener: (context, state) {
|
||||||
TabsEvent.openPlugin(
|
final page = state.lastCreatedPage;
|
||||||
plugin: state.lastCreatedPage!.plugin(),
|
if (page == null || page.id.isEmpty) {
|
||||||
),
|
// open the blank page
|
||||||
),
|
context.read<TabsBloc>().add(
|
||||||
|
TabsEvent.openPlugin(
|
||||||
|
plugin: BlankPagePlugin(),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
context.read<TabsBloc>().add(
|
||||||
|
TabsEvent.openPlugin(
|
||||||
|
plugin: state.lastCreatedPage!.plugin(),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
},
|
||||||
),
|
),
|
||||||
BlocListener<ActionNavigationBloc, ActionNavigationState>(
|
BlocListener<ActionNavigationBloc, ActionNavigationState>(
|
||||||
listenWhen: (_, curr) => curr.action != null,
|
listenWhen: (_, curr) => curr.action != null,
|
||||||
@ -151,23 +165,27 @@ class HomeSideBar extends StatelessWidget {
|
|||||||
if (actionType == UserWorkspaceActionType.create ||
|
if (actionType == UserWorkspaceActionType.create ||
|
||||||
actionType == UserWorkspaceActionType.delete ||
|
actionType == UserWorkspaceActionType.delete ||
|
||||||
actionType == UserWorkspaceActionType.open) {
|
actionType == UserWorkspaceActionType.open) {
|
||||||
context.read<SidebarSectionsBloc>().add(
|
if (context.read<SpaceBloc>().state.spaces.isEmpty) {
|
||||||
SidebarSectionsEvent.reload(
|
context.read<SidebarSectionsBloc>().add(
|
||||||
userProfile,
|
SidebarSectionsEvent.reload(
|
||||||
state.currentWorkspace?.workspaceId ??
|
userProfile,
|
||||||
workspaceSetting.workspaceId,
|
state.currentWorkspace?.workspaceId ??
|
||||||
),
|
workspaceSetting.workspaceId,
|
||||||
);
|
),
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
context.read<SpaceBloc>().add(
|
||||||
|
SpaceEvent.reset(
|
||||||
|
userProfile,
|
||||||
|
state.currentWorkspace?.workspaceId ??
|
||||||
|
workspaceSetting.workspaceId,
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
context
|
context
|
||||||
.read<FavoriteBloc>()
|
.read<FavoriteBloc>()
|
||||||
.add(const FavoriteEvent.fetchFavorites());
|
.add(const FavoriteEvent.fetchFavorites());
|
||||||
context.read<SpaceBloc>().add(
|
|
||||||
SpaceEvent.reset(
|
|
||||||
userProfile,
|
|
||||||
state.currentWorkspace?.workspaceId ??
|
|
||||||
workspaceSetting.workspaceId,
|
|
||||||
),
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
),
|
),
|
||||||
|
@ -50,7 +50,13 @@ class _CreateSpacePopupState extends State<CreateSpacePopup> {
|
|||||||
),
|
),
|
||||||
),
|
),
|
||||||
const VSpace(8.0),
|
const VSpace(8.0),
|
||||||
_SpaceNameTextField(onChanged: (value) => spaceName = value),
|
_SpaceNameTextField(
|
||||||
|
onChanged: (value) => spaceName = value,
|
||||||
|
onSubmitted: (value) {
|
||||||
|
spaceName = value;
|
||||||
|
_createSpace();
|
||||||
|
},
|
||||||
|
),
|
||||||
const VSpace(20.0),
|
const VSpace(20.0),
|
||||||
SpacePermissionSwitch(
|
SpacePermissionSwitch(
|
||||||
onPermissionChanged: (value) => spacePermission = value,
|
onPermissionChanged: (value) => spacePermission = value,
|
||||||
@ -59,29 +65,36 @@ class _CreateSpacePopupState extends State<CreateSpacePopup> {
|
|||||||
SpaceCancelOrConfirmButton(
|
SpaceCancelOrConfirmButton(
|
||||||
confirmButtonName: LocaleKeys.button_create.tr(),
|
confirmButtonName: LocaleKeys.button_create.tr(),
|
||||||
onCancel: () => Navigator.of(context).pop(),
|
onCancel: () => Navigator.of(context).pop(),
|
||||||
onConfirm: () {
|
onConfirm: () => _createSpace(),
|
||||||
context.read<SpaceBloc>().add(
|
|
||||||
SpaceEvent.create(
|
|
||||||
name: spaceName,
|
|
||||||
icon: spaceIcon,
|
|
||||||
iconColor: spaceIconColor,
|
|
||||||
permission: spacePermission,
|
|
||||||
),
|
|
||||||
);
|
|
||||||
|
|
||||||
Navigator.of(context).pop();
|
|
||||||
},
|
|
||||||
),
|
),
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void _createSpace() {
|
||||||
|
context.read<SpaceBloc>().add(
|
||||||
|
SpaceEvent.create(
|
||||||
|
name: spaceName,
|
||||||
|
icon: spaceIcon,
|
||||||
|
iconColor: spaceIconColor,
|
||||||
|
permission: spacePermission,
|
||||||
|
createNewPageByDefault: true,
|
||||||
|
),
|
||||||
|
);
|
||||||
|
|
||||||
|
Navigator.of(context).pop();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class _SpaceNameTextField extends StatelessWidget {
|
class _SpaceNameTextField extends StatelessWidget {
|
||||||
const _SpaceNameTextField({required this.onChanged});
|
const _SpaceNameTextField({
|
||||||
|
required this.onChanged,
|
||||||
|
required this.onSubmitted,
|
||||||
|
});
|
||||||
|
|
||||||
final void Function(String name) onChanged;
|
final void Function(String name) onChanged;
|
||||||
|
final void Function(String name) onSubmitted;
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
@ -98,8 +111,9 @@ class _SpaceNameTextField extends StatelessWidget {
|
|||||||
SizedBox(
|
SizedBox(
|
||||||
height: 40,
|
height: 40,
|
||||||
child: FlowyTextField(
|
child: FlowyTextField(
|
||||||
text: LocaleKeys.space_defaultSpaceName.tr(),
|
hintText: LocaleKeys.space_spaceName.tr(),
|
||||||
onChanged: onChanged,
|
onChanged: onChanged,
|
||||||
|
onSubmitted: onSubmitted,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
],
|
],
|
||||||
|
@ -199,7 +199,7 @@ class SpaceCancelOrConfirmButton extends StatelessWidget {
|
|||||||
radius: BorderRadius.circular(8),
|
radius: BorderRadius.circular(8),
|
||||||
text: FlowyText.regular(
|
text: FlowyText.regular(
|
||||||
confirmButtonName,
|
confirmButtonName,
|
||||||
color: Theme.of(context).colorScheme.onPrimary,
|
color: Colors.white,
|
||||||
),
|
),
|
||||||
onTap: onConfirm,
|
onTap: onConfirm,
|
||||||
),
|
),
|
||||||
|
@ -7,6 +7,7 @@ import 'package:appflowy/workspace/application/tabs/tabs_bloc.dart';
|
|||||||
import 'package:appflowy/workspace/application/view/view_bloc.dart';
|
import 'package:appflowy/workspace/application/view/view_bloc.dart';
|
||||||
import 'package:appflowy/workspace/application/view/view_ext.dart';
|
import 'package:appflowy/workspace/application/view/view_ext.dart';
|
||||||
import 'package:appflowy/workspace/presentation/home/home_sizes.dart';
|
import 'package:appflowy/workspace/presentation/home/home_sizes.dart';
|
||||||
|
import 'package:appflowy/workspace/presentation/home/hotkeys.dart';
|
||||||
import 'package:appflowy/workspace/presentation/home/menu/menu_shared_state.dart';
|
import 'package:appflowy/workspace/presentation/home/menu/menu_shared_state.dart';
|
||||||
import 'package:appflowy/workspace/presentation/home/menu/sidebar/favorites/favorite_folder.dart';
|
import 'package:appflowy/workspace/presentation/home/menu/sidebar/favorites/favorite_folder.dart';
|
||||||
import 'package:appflowy/workspace/presentation/home/menu/sidebar/shared/rename_view_dialog.dart';
|
import 'package:appflowy/workspace/presentation/home/menu/sidebar/shared/rename_view_dialog.dart';
|
||||||
@ -79,6 +80,18 @@ class _SpaceState extends State<_Space> {
|
|||||||
final PropertyValueNotifier<bool> isExpandedNotifier =
|
final PropertyValueNotifier<bool> isExpandedNotifier =
|
||||||
PropertyValueNotifier(false);
|
PropertyValueNotifier(false);
|
||||||
|
|
||||||
|
@override
|
||||||
|
void initState() {
|
||||||
|
super.initState();
|
||||||
|
switchToTheNextSpace.addListener(_switchToNextSpace);
|
||||||
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
void dispose() {
|
||||||
|
switchToTheNextSpace.removeListener(_switchToNextSpace);
|
||||||
|
super.dispose();
|
||||||
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
return BlocBuilder<SpaceBloc, SpaceState>(
|
return BlocBuilder<SpaceBloc, SpaceState>(
|
||||||
@ -142,10 +155,6 @@ class _SpaceState extends State<_Space> {
|
|||||||
SpaceEvent.createPage(
|
SpaceEvent.createPage(
|
||||||
name: viewName,
|
name: viewName,
|
||||||
index: 0,
|
index: 0,
|
||||||
viewSection:
|
|
||||||
space.spacePermission == SpacePermission.publicToAll
|
|
||||||
? ViewSectionPB.Public
|
|
||||||
: ViewSectionPB.Private,
|
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -154,6 +163,10 @@ class _SpaceState extends State<_Space> {
|
|||||||
},
|
},
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void _switchToNextSpace() {
|
||||||
|
context.read<SpaceBloc>().add(const SpaceEvent.switchToNextSpace());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class _Pages extends StatelessWidget {
|
class _Pages extends StatelessWidget {
|
||||||
|
@ -1,5 +1,8 @@
|
|||||||
|
import 'dart:io';
|
||||||
|
|
||||||
import 'package:appflowy/generated/flowy_svgs.g.dart';
|
import 'package:appflowy/generated/flowy_svgs.g.dart';
|
||||||
import 'package:appflowy/generated/locale_keys.g.dart';
|
import 'package:appflowy/generated/locale_keys.g.dart';
|
||||||
|
import 'package:appflowy/util/theme_extension.dart';
|
||||||
import 'package:appflowy/workspace/application/sidebar/space/space_bloc.dart';
|
import 'package:appflowy/workspace/application/sidebar/space/space_bloc.dart';
|
||||||
import 'package:appflowy/workspace/presentation/home/home_sizes.dart';
|
import 'package:appflowy/workspace/presentation/home/home_sizes.dart';
|
||||||
import 'package:appflowy/workspace/presentation/home/menu/sidebar/space/manage_space_popup.dart';
|
import 'package:appflowy/workspace/presentation/home/menu/sidebar/space/manage_space_popup.dart';
|
||||||
@ -13,6 +16,7 @@ import 'package:appflowy_backend/protobuf/flowy-folder/view.pb.dart';
|
|||||||
import 'package:appflowy_popover/appflowy_popover.dart';
|
import 'package:appflowy_popover/appflowy_popover.dart';
|
||||||
import 'package:easy_localization/easy_localization.dart';
|
import 'package:easy_localization/easy_localization.dart';
|
||||||
import 'package:flowy_infra_ui/flowy_infra_ui.dart';
|
import 'package:flowy_infra_ui/flowy_infra_ui.dart';
|
||||||
|
import 'package:flowy_infra_ui/widget/flowy_tooltip.dart';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||||
|
|
||||||
@ -70,7 +74,6 @@ class _SidebarSpaceHeaderState extends State<SidebarSpaceHeader> {
|
|||||||
height: HomeSizes.workspaceSectionHeight,
|
height: HomeSizes.workspaceSectionHeight,
|
||||||
child: FlowyButton(
|
child: FlowyButton(
|
||||||
margin: const EdgeInsets.only(left: 6.0, right: 4.0),
|
margin: const EdgeInsets.only(left: 6.0, right: 4.0),
|
||||||
// rightIcon: _buildRightIcon(),
|
|
||||||
iconPadding: 10.0,
|
iconPadding: 10.0,
|
||||||
text: _buildChild(),
|
text: _buildChild(),
|
||||||
rightIcon: const HSpace(60.0),
|
rightIcon: const HSpace(60.0),
|
||||||
@ -88,30 +91,50 @@ class _SidebarSpaceHeaderState extends State<SidebarSpaceHeader> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
Widget _buildChild() {
|
Widget _buildChild() {
|
||||||
return Row(
|
final color = Theme.of(context).isLightMode ? Colors.white : Colors.black;
|
||||||
|
final textSpan = TextSpan(
|
||||||
children: [
|
children: [
|
||||||
SpaceIcon(
|
TextSpan(
|
||||||
dimension: 20,
|
text: '${LocaleKeys.space_quicklySwitch.tr()}\n',
|
||||||
space: widget.space,
|
style:
|
||||||
cornerRadius: 6.0,
|
Theme.of(context).tooltipTheme.textStyle!.copyWith(color: color),
|
||||||
),
|
),
|
||||||
const HSpace(10),
|
TextSpan(
|
||||||
Flexible(
|
text: Platform.isMacOS ? '⌘+O' : 'Ctrl+O',
|
||||||
child: FlowyText.medium(
|
style: Theme.of(context)
|
||||||
widget.space.name,
|
.tooltipTheme
|
||||||
lineHeight: 1.15,
|
.textStyle!
|
||||||
fontSize: 14.0,
|
.copyWith(color: Theme.of(context).hintColor),
|
||||||
overflow: TextOverflow.ellipsis,
|
|
||||||
),
|
|
||||||
),
|
|
||||||
const HSpace(4.0),
|
|
||||||
FlowySvg(
|
|
||||||
widget.isExpanded
|
|
||||||
? FlowySvgs.workspace_drop_down_menu_show_s
|
|
||||||
: FlowySvgs.workspace_drop_down_menu_hide_s,
|
|
||||||
),
|
),
|
||||||
],
|
],
|
||||||
);
|
);
|
||||||
|
return FlowyTooltip(
|
||||||
|
richMessage: textSpan,
|
||||||
|
child: Row(
|
||||||
|
children: [
|
||||||
|
SpaceIcon(
|
||||||
|
dimension: 20,
|
||||||
|
space: widget.space,
|
||||||
|
cornerRadius: 6.0,
|
||||||
|
),
|
||||||
|
const HSpace(10),
|
||||||
|
Flexible(
|
||||||
|
child: FlowyText.medium(
|
||||||
|
widget.space.name,
|
||||||
|
lineHeight: 1.15,
|
||||||
|
fontSize: 14.0,
|
||||||
|
overflow: TextOverflow.ellipsis,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
const HSpace(4.0),
|
||||||
|
FlowySvg(
|
||||||
|
widget.isExpanded
|
||||||
|
? FlowySvgs.workspace_drop_down_menu_show_s
|
||||||
|
: FlowySvgs.workspace_drop_down_menu_hide_s,
|
||||||
|
),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
Widget _buildRightIcon() {
|
Widget _buildRightIcon() {
|
||||||
|
@ -55,7 +55,6 @@ extension ViewMoreActionTypeExtension on SpaceMoreActionType {
|
|||||||
Widget get rightIcon {
|
Widget get rightIcon {
|
||||||
switch (this) {
|
switch (this) {
|
||||||
case SpaceMoreActionType.changeIcon:
|
case SpaceMoreActionType.changeIcon:
|
||||||
return const FlowySvg(FlowySvgs.view_item_right_arrow_s);
|
|
||||||
case SpaceMoreActionType.rename:
|
case SpaceMoreActionType.rename:
|
||||||
case SpaceMoreActionType.collapseAllPages:
|
case SpaceMoreActionType.collapseAllPages:
|
||||||
case SpaceMoreActionType.divider:
|
case SpaceMoreActionType.divider:
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
import 'package:appflowy/generated/flowy_svgs.g.dart';
|
import 'package:appflowy/generated/flowy_svgs.g.dart';
|
||||||
import 'package:appflowy/generated/locale_keys.g.dart';
|
import 'package:appflowy/generated/locale_keys.g.dart';
|
||||||
|
import 'package:appflowy/util/theme_extension.dart';
|
||||||
import 'package:appflowy/workspace/application/sidebar/space/space_bloc.dart';
|
import 'package:appflowy/workspace/application/sidebar/space/space_bloc.dart';
|
||||||
import 'package:easy_localization/easy_localization.dart';
|
import 'package:easy_localization/easy_localization.dart';
|
||||||
import 'package:flowy_infra_ui/flowy_infra_ui.dart';
|
import 'package:flowy_infra_ui/flowy_infra_ui.dart';
|
||||||
@ -22,7 +23,9 @@ class _SpaceMigrationState extends State<SpaceMigration> {
|
|||||||
padding: const EdgeInsets.all(12),
|
padding: const EdgeInsets.all(12),
|
||||||
clipBehavior: Clip.antiAlias,
|
clipBehavior: Clip.antiAlias,
|
||||||
decoration: ShapeDecoration(
|
decoration: ShapeDecoration(
|
||||||
color: const Color(0x66F5EAFF),
|
color: Theme.of(context).isLightMode
|
||||||
|
? const Color(0x66F5EAFF)
|
||||||
|
: const Color(0x1AFFFFFF),
|
||||||
shape: RoundedRectangleBorder(
|
shape: RoundedRectangleBorder(
|
||||||
side: const BorderSide(
|
side: const BorderSide(
|
||||||
strokeAlign: BorderSide.strokeAlignOutside,
|
strokeAlign: BorderSide.strokeAlignOutside,
|
||||||
@ -129,13 +132,6 @@ class _MigrationTitle extends StatelessWidget {
|
|||||||
lineHeight: 1.2,
|
lineHeight: 1.2,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
GestureDetector(
|
|
||||||
onTap: onClose,
|
|
||||||
child: const Padding(
|
|
||||||
padding: EdgeInsets.only(top: 3.0),
|
|
||||||
child: FlowySvg(FlowySvgs.upgrade_close_s),
|
|
||||||
),
|
|
||||||
),
|
|
||||||
],
|
],
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -82,7 +82,6 @@ extension ViewMoreActionTypeExtension on ViewMoreActionType {
|
|||||||
switch (this) {
|
switch (this) {
|
||||||
case ViewMoreActionType.changeIcon:
|
case ViewMoreActionType.changeIcon:
|
||||||
case ViewMoreActionType.moveTo:
|
case ViewMoreActionType.moveTo:
|
||||||
return const FlowySvg(FlowySvgs.view_item_right_arrow_s);
|
|
||||||
case ViewMoreActionType.favorite:
|
case ViewMoreActionType.favorite:
|
||||||
case ViewMoreActionType.unFavorite:
|
case ViewMoreActionType.unFavorite:
|
||||||
case ViewMoreActionType.duplicate:
|
case ViewMoreActionType.duplicate:
|
||||||
|
@ -53,8 +53,8 @@ packages:
|
|||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
path: "."
|
path: "."
|
||||||
ref: d73e8893d1f1b06566ebed5868698be75c6b7f93
|
ref: b5da6e4
|
||||||
resolved-ref: d73e8893d1f1b06566ebed5868698be75c6b7f93
|
resolved-ref: b5da6e4afcb832ca74f588d7007824b02b5d51de
|
||||||
url: "https://github.com/AppFlowy-IO/appflowy-editor.git"
|
url: "https://github.com/AppFlowy-IO/appflowy-editor.git"
|
||||||
source: git
|
source: git
|
||||||
version: "2.5.1"
|
version: "2.5.1"
|
||||||
|
@ -186,7 +186,7 @@ dependency_overrides:
|
|||||||
appflowy_editor:
|
appflowy_editor:
|
||||||
git:
|
git:
|
||||||
url: https://github.com/AppFlowy-IO/appflowy-editor.git
|
url: https://github.com/AppFlowy-IO/appflowy-editor.git
|
||||||
ref: "d73e8893d1f1b06566ebed5868698be75c6b7f93"
|
ref: "b5da6e4"
|
||||||
|
|
||||||
sheet:
|
sheet:
|
||||||
git:
|
git:
|
||||||
|
@ -1,5 +1,4 @@
|
|||||||
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
|
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||||
<path d="M5.89999 13.8666L5.89999 3.36531L5.89999 2.1333H3.59999C2.49542 2.1333 1.59999 3.02874 1.59999 4.1333L1.59999 11.8666C1.59999 12.9712 2.49542 13.8666 3.59999 13.8666H5.89999Z" stroke="#171717" stroke-width="1.1" stroke-linecap="round" stroke-linejoin="round"/>
|
<path d="M6.89922 12.9772V3.0232C6.89922 2.0782 6.50769 1.7002 5.53498 1.7002H3.06345C2.09075 1.7002 1.69922 2.0782 1.69922 3.0232V12.9772C1.69922 13.9222 2.09075 14.3002 3.06345 14.3002H5.53498C6.50769 14.3002 6.89922 13.9222 6.89922 12.9772Z" stroke="#171717" stroke-linecap="round" stroke-linejoin="round"/>
|
||||||
<path d="M5.89999 2.1333V12.6346V13.8666H10.2V12.6346V2.1333H5.89999Z" stroke="#171717" stroke-width="1.1" stroke-linecap="round" stroke-linejoin="round"/>
|
<path d="M14.2996 8.78519V3.0652C14.2996 2.0902 13.9081 1.7002 12.9354 1.7002H10.4638C9.49114 1.7002 9.09961 2.0902 9.09961 3.0652V8.78519C9.09961 9.76019 9.49114 10.1502 10.4638 10.1502H12.9354C13.9081 10.1502 14.2996 9.76019 14.2996 8.78519Z" stroke="#171717" stroke-linecap="round" stroke-linejoin="round"/>
|
||||||
<path d="M10.2 2.1333V12.6346V13.8666H12.5C13.6046 13.8666 14.5 12.9712 14.5 11.8666V4.1333C14.5 3.02873 13.6046 2.1333 12.5 2.1333H10.2Z" stroke="#171717" stroke-width="1.1" stroke-linecap="round" stroke-linejoin="round"/>
|
|
||||||
</svg>
|
</svg>
|
||||||
|
Before Width: | Height: | Size: 753 B After Width: | Height: | Size: 725 B |
@ -1,7 +1,3 @@
|
|||||||
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
|
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||||
<g opacity="0.6">
|
<path d="M9.39568 7.6963L6.91032 5.56599C6.65085 5.34358 6.25 5.52795 6.25 5.86969L6.25 10.1303C6.25 10.4721 6.65085 10.6564 6.91032 10.434L9.39568 8.3037C9.58192 8.14406 9.58192 7.85594 9.39568 7.6963Z" fill="#333333"/>
|
||||||
<path d="M4.23516 7.99941C4.23516 8.60693 3.74267 9.09941 3.13516 9.09941C2.52764 9.09941 2.03516 8.60693 2.03516 7.99941C2.03516 7.3919 2.52764 6.89941 3.13516 6.89941C3.74267 6.89941 4.23516 7.3919 4.23516 7.99941Z" fill="#171717"/>
|
|
||||||
<path d="M9.10234 7.99941C9.10234 8.60693 8.60986 9.09941 8.00234 9.09941C7.39483 9.09941 6.90234 8.60693 6.90234 7.99941C6.90234 7.3919 7.39483 6.89941 8.00234 6.89941C8.60986 6.89941 9.10234 7.3919 9.10234 7.99941Z" fill="#171717"/>
|
|
||||||
<path d="M13.9695 7.99941C13.9695 8.60693 13.477 9.09941 12.8695 9.09941C12.262 9.09941 11.7695 8.60693 11.7695 7.99941C11.7695 7.3919 12.262 6.89941 12.8695 6.89941C13.477 6.89941 13.9695 7.3919 13.9695 7.99941Z" fill="#171717"/>
|
|
||||||
</g>
|
|
||||||
</svg>
|
</svg>
|
Before Width: | Height: | Size: 851 B After Width: | Height: | Size: 331 B |
@ -1,3 +1,3 @@
|
|||||||
<svg width="8" height="10" viewBox="0 0 8 10" fill="none" xmlns="http://www.w3.org/2000/svg">
|
<svg width="12" height="12" viewBox="0 0 12 12" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||||
<path opacity="0.5" d="M6.7881 4.14174V3.56457C6.7881 2.82926 6.7881 0.599609 4 0.599609C1.2119 0.599609 1.2119 2.82926 1.2119 3.56457V4.14174C0.304836 4.35522 0 4.97984 0 6.33186V7.12252C0 8.86196 0.505579 9.39961 2.14127 9.39961H5.85873C7.49442 9.39961 8 8.86196 8 7.12252V6.33186C8 4.97984 7.69516 4.35522 6.7881 4.14174ZM4 7.59692C3.54647 7.59692 3.18217 7.20949 3.18217 6.72719C3.18217 6.24489 3.54647 5.85746 4 5.85746C4.45353 5.85746 4.81782 6.24489 4.81782 6.72719C4.81782 7.20949 4.45353 7.59692 4 7.59692ZM5.67286 4.05477H2.32714V3.56457C2.32714 2.41021 2.5948 1.78559 4 1.78559C5.4052 1.78559 5.67286 2.41021 5.67286 3.56457V4.05477Z" fill="#171717"/>
|
<path opacity="0.4" fill-rule="evenodd" clip-rule="evenodd" d="M8.78714 4.75039V4.16515C8.78714 3.42984 8.6 1.25 5.99904 1.25C3.3 1.25 3.21094 3.42984 3.21094 4.16515V4.75039L3.38817 4.73529L3.2119 4.75123C2.30484 4.99873 2 5.7229 2 7.29041V8.20709C2 10.2238 2.50558 10.9996 4.14127 10.9996H7.85873C9.49442 10.9996 10 10.2238 10 8.20709V7.29041C10 5.7229 9.69516 4.99873 8.7881 4.75123L8.64331 4.73813L8.78714 4.75039ZM4.32618 4.16515V4.65048L7.6719 4.65039V4.16515C7.6719 3.0108 7.3 2.3002 5.99904 2.3002C4.65 2.3002 4.32618 3.0108 4.32618 4.16515ZM6.00078 8.95078C6.66352 8.95078 7.20078 8.41352 7.20078 7.75078C7.20078 7.08804 6.66352 6.55078 6.00078 6.55078C5.33804 6.55078 4.80078 7.08804 4.80078 7.75078C4.80078 8.41352 5.33804 8.95078 6.00078 8.95078Z" fill="#171717"/>
|
||||||
</svg>
|
</svg>
|
||||||
|
Before Width: | Height: | Size: 764 B After Width: | Height: | Size: 880 B |
@ -1,5 +1,4 @@
|
|||||||
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
|
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||||
<path d="M4.16484 3.1001H8.96484L8.96484 15.1001C8.96484 15.6524 8.51713 16.1001 7.96484 16.1001H4.16484C3.33642 16.1001 2.66484 15.4285 2.66484 14.6001L2.66484 4.6001C2.66484 3.77167 3.33642 3.1001 4.16484 3.1001Z" stroke="#49CD57" stroke-width="1.58" stroke-linecap="round" stroke-linejoin="round"/>
|
<path d="M10.2023 19.4658V4.53479C10.2023 3.11729 9.61505 2.55029 8.15599 2.55029H4.4487C2.98964 2.55029 2.40234 3.11729 2.40234 4.53479V19.4658C2.40234 20.8833 2.98964 21.4503 4.4487 21.4503H8.15599C9.61505 21.4503 10.2023 20.8833 10.2023 19.4658Z" stroke="#49CD57" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||||
<path d="M15.2648 3.1001H8.96484V19.4001C8.96484 20.2285 9.63642 20.9001 10.4648 20.9001H13.7648C14.5933 20.9001 15.2648 20.2285 15.2648 19.4001V3.1001Z" stroke="#49CD57" stroke-width="1.58" stroke-linecap="round" stroke-linejoin="round"/>
|
<path d="M21.6008 13.1778V4.59779C21.6008 3.13529 21.0135 2.55029 19.5544 2.55029H15.8471C14.3881 2.55029 13.8008 3.13529 13.8008 4.59779V13.1778C13.8008 14.6403 14.3881 15.2253 15.8471 15.2253H19.5544C21.0135 15.2253 21.6008 14.6403 21.6008 13.1778Z" stroke="#49CD57" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||||
<path d="M20.0656 12.6001H16.2656C15.7133 12.6001 15.2656 12.1524 15.2656 11.6001V3.1001H20.0656C20.8941 3.1001 21.5656 3.77167 21.5656 4.6001V11.1001C21.5656 11.9285 20.8941 12.6001 20.0656 12.6001Z" stroke="#49CD57" stroke-width="1.58" stroke-linecap="round" stroke-linejoin="round"/>
|
|
||||||
</svg>
|
</svg>
|
||||||
|
Before Width: | Height: | Size: 932 B After Width: | Height: | Size: 775 B |
@ -260,7 +260,7 @@
|
|||||||
"recent": "Recent",
|
"recent": "Recent",
|
||||||
"today": "Today",
|
"today": "Today",
|
||||||
"thisWeek": "This week",
|
"thisWeek": "This week",
|
||||||
"others": "Others",
|
"others": "Other favorites",
|
||||||
"justNow": "just now",
|
"justNow": "just now",
|
||||||
"minutesAgo": "{count} minutes ago",
|
"minutesAgo": "{count} minutes ago",
|
||||||
"lastViewed": "Last viewed",
|
"lastViewed": "Last viewed",
|
||||||
@ -1891,16 +1891,16 @@
|
|||||||
"clearSearchTooltip": "Clear search field"
|
"clearSearchTooltip": "Clear search field"
|
||||||
},
|
},
|
||||||
"space": {
|
"space": {
|
||||||
"delete": "Delete space",
|
"delete": "Delete",
|
||||||
"deleteConfirmation": "Are you sure you want to delete this space?",
|
"deleteConfirmation": "Delete: {Space Name}",
|
||||||
"deleteConfirmationDescription": "This action cannot be undone, and will remove the pages and data in this space.",
|
"deleteConfirmationDescription": "All pages within this Space will be deleted and moved to Trash.",
|
||||||
"rename": "Rename space",
|
"rename": "Rename Space",
|
||||||
"changeIcon": "Change icon",
|
"changeIcon": "Change icon",
|
||||||
"manage": "Manage space",
|
"manage": "Manage Space",
|
||||||
"addNewSpace": "Add new space",
|
"addNewSpace": "Create Space",
|
||||||
"collapseAllSubPages": "Collapse all subpages",
|
"collapseAllSubPages": "Collapse all subpages",
|
||||||
"createNewSpace": "Create new space",
|
"createNewSpace": "Create a new space",
|
||||||
"createSpaceDescription": "Separate your tabs for life, work, project and more",
|
"createSpaceDescription": "Create multiple public and private spaces to better organize your work.",
|
||||||
"spaceName": "Space name",
|
"spaceName": "Space name",
|
||||||
"permission": "Permission",
|
"permission": "Permission",
|
||||||
"publicPermission": "Public",
|
"publicPermission": "Public",
|
||||||
@ -1910,14 +1910,15 @@
|
|||||||
"spaceIconBackground": "Background color",
|
"spaceIconBackground": "Background color",
|
||||||
"spaceIcon": "Icon",
|
"spaceIcon": "Icon",
|
||||||
"dangerZone": "Danger Zone",
|
"dangerZone": "Danger Zone",
|
||||||
"unableToDeleteLastSpace": "Cannot delete the last space",
|
"unableToDeleteLastSpace": "Unable to delete the last Space",
|
||||||
"unableToDeleteSpaceNotCreatedByYou": "Cannot delete a space created by others",
|
"unableToDeleteSpaceNotCreatedByYou": "Unable to delete Spaces created by others",
|
||||||
"enableSpacesForYourWorkspace": "Enable spaces for your workspace",
|
"enableSpacesForYourWorkspace": "Enable Spaces for your workspace",
|
||||||
"title": "Spaces",
|
"title": "Spaces",
|
||||||
"defaultSpaceName": "General",
|
"defaultSpaceName": "General",
|
||||||
"upgradeSpaceTitle": "Enable Spaces for your workspace",
|
"upgradeSpaceTitle": "Enable Spaces",
|
||||||
"upgradeSpaceDescription": "Create multiple public and private spaces to better organize your work.",
|
"upgradeSpaceDescription": "Create multiple public and private Spaces to better organize your workspace.",
|
||||||
"upgrade": "Upgrade",
|
"upgrade": "Update",
|
||||||
"upgradeYourSpace": "Upgrade your space"
|
"upgradeYourSpace": "Create multiple Spaces",
|
||||||
|
"quicklySwitch": "Quickly switch to the next space"
|
||||||
}
|
}
|
||||||
}
|
}
|