Skip to content

Commit

Permalink
Integrate file editors application menu (#9809)
Browse files Browse the repository at this point in the history
* Integrate file editors in application menu
  • Loading branch information
lookacat authored Oct 23, 2023
1 parent bf1194a commit d8b2349
Show file tree
Hide file tree
Showing 35 changed files with 822 additions and 270 deletions.
32 changes: 23 additions & 9 deletions packages/design-system/src/components/OcResource/OcResource.vue
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@
<oc-resource-name
:key="resource.name"
:name="resource.name"
:path-prefix="pathPrefix"
:extension="resource.extension"
:type="resource.type"
:full-path="resource.path"
Expand Down Expand Up @@ -107,6 +108,14 @@ export default defineComponent({
type: Object as PropType<Resource>,
required: true
},
/**
* The prefix that will be shown in the path
*/
pathPrefix: {
type: String,
required: false,
default: ''
},
/**
* The resource folder link
*/
Expand Down Expand Up @@ -301,6 +310,20 @@ export default defineComponent({
&-indicators {
display: flex;
a {
&:hover {
background-color: var(--oc-color-input-bg);
border-radius: 2px;
}
.text {
&:hover {
color: var(--oc-color-text-default);
text-decoration: underline;
}
}
}
.parent-folder {
display: flex;
align-items: center;
Expand All @@ -315,15 +338,6 @@ export default defineComponent({
.text {
font-size: 0.8125rem;
color: var(--oc-color-text-muted);
&:hover {
color: var(--oc-color-text-default);
text-decoration: underline;
}
}
&:hover {
background-color: var(--oc-color-input-bg);
border-radius: 2px;
}
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@

<script lang="ts">
import { defineComponent } from 'vue'
import path from 'path'
export default defineComponent({
name: 'OcResourceName',
Expand All @@ -34,6 +35,14 @@ export default defineComponent({
type: String,
required: true
},
/**
* The prefix that will be shown in the path
*/
pathPrefix: {
type: String,
required: false,
default: ''
},
/**
* The extension of the resource, if there is one
*/
Expand Down Expand Up @@ -123,6 +132,9 @@ export default defineComponent({
if (this.displayPath === this.fullPath) {
return null
}
if (this.pathPrefix) {
return path.join(this.pathPrefix, this.fullPath)
}
return this.fullPath
},
Expand All @@ -146,6 +158,7 @@ export default defineComponent({
&-name {
display: flex;
min-width: 0;
&:hover {
text-decoration: underline;
text-decoration-color: var(--oc-color-text-default);
Expand All @@ -167,13 +180,21 @@ export default defineComponent({

<docs>
```js
<oc-resource-name full-path="documents/notes.txt" name="notes.txt" extension="txt" type="file" :is-extension-displayed="false" />
<oc-resource-name full-path="documents/notes.txt" name="notes.txt" extension="txt" type="file" />
<oc-resource-name full-path="documents/notes.txt" name="super-long-file-name-which-will-be-truncated-when-exceeding-the-screen-space-while-still-preserving-the-file-extension-at-the-end.txt" extension="txt" type="file" />
<oc-resource-name full-path="documents/notes.txt" name="super-long-file-name-which-will-not-be-truncated-when-you-disable-it-manually-via-the-truncate-property.txt" extension="txt" type="file" :truncate-name="false" />
<oc-resource-name full-path="images/nature/forest.jpg" :is-path-displayed="true" name="forest.jpg" extension="jpg" type="file" />
<oc-resource-name full-path="super-long-path-to-a-subfolder-which-is-a-lot-of-levels-away-from–the-root-super-long-path-to-a-subfolder-which-is-a-lot-of-levels-away-from–the-root/asdf.txt" :is-path-displayed="true" name="asdf.txt" extension="txt" type="file" />
<oc-resource-name full-path="some-folder" name="regular-folder" extension="" type="folder" />
<oc-resource-name full-path="folder-name-with.dot" name="folder-name-with.dot" extension="" type="folder" />
<oc-resource-name full-path="documents/notes.txt" name="notes.txt" extension="txt" type="file"
:is-extension-displayed="false"/>
<oc-resource-name full-path="documents/notes.txt" name="notes.txt" extension="txt" type="file"/>
<oc-resource-name full-path="documents/notes.txt"
name="super-long-file-name-which-will-be-truncated-when-exceeding-the-screen-space-while-still-preserving-the-file-extension-at-the-end.txt"
extension="txt" type="file"/>
<oc-resource-name full-path="documents/notes.txt"
name="super-long-file-name-which-will-not-be-truncated-when-you-disable-it-manually-via-the-truncate-property.txt"
extension="txt" type="file" :truncate-name="false"/>
<oc-resource-name full-path="images/nature/forest.jpg" :is-path-displayed="true" name="forest.jpg" extension="jpg"
type="file"/>
<oc-resource-name
full-path="super-long-path-to-a-subfolder-which-is-a-lot-of-levels-away-from–the-root-super-long-path-to-a-subfolder-which-is-a-lot-of-levels-away-from–the-root/asdf.txt"
:is-path-displayed="true" name="asdf.txt" extension="txt" type="file"/>
<oc-resource-name full-path="some-folder" name="regular-folder" extension="" type="folder"/>
<oc-resource-name full-path="folder-name-with.dot" name="folder-name-with.dot" extension="" type="folder"/>
```
</docs>
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ exports[`OcTile component renders default space correctly 1`] = `
<div class="oc-card-body oc-p-s">
<div class="oc-flex oc-flex-between oc-flex-middle">
<div class="oc-flex oc-flex-middle oc-text-truncate resource-name-wrapper">
<oc-resource-stub isextensiondisplayed="true" isicondisplayed="false" ispathdisplayed="false" isresourceclickable="true" isthumbnaildisplayed="true" parentfoldername="" resource="[object Object]"></oc-resource-stub>
<oc-resource-stub isextensiondisplayed="true" isicondisplayed="false" ispathdisplayed="false" isresourceclickable="true" isthumbnaildisplayed="true" parentfoldername="" pathprefix="" resource="[object Object]"></oc-resource-stub>
</div>
<div class="oc-flex oc-flex-middle">
<!-- Slot for individual actions -->
Expand All @@ -40,7 +40,7 @@ exports[`OcTile component renders disabled space correctly 1`] = `
<div class="oc-card-body oc-p-s">
<div class="oc-flex oc-flex-between oc-flex-middle">
<div class="oc-flex oc-flex-middle oc-text-truncate resource-name-wrapper">
<oc-resource-stub isextensiondisplayed="true" isicondisplayed="false" ispathdisplayed="false" isresourceclickable="true" isthumbnaildisplayed="true" parentfoldername="" resource="[object Object]"></oc-resource-stub>
<oc-resource-stub isextensiondisplayed="true" isicondisplayed="false" ispathdisplayed="false" isresourceclickable="true" isthumbnaildisplayed="true" parentfoldername="" pathprefix="" resource="[object Object]"></oc-resource-stub>
</div>
<div class="oc-flex oc-flex-middle">
<!-- Slot for individual actions -->
Expand Down
9 changes: 8 additions & 1 deletion packages/web-app-admin-settings/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import Groups from './views/Groups.vue'
import Spaces from './views/Spaces.vue'
import { Ability } from '@ownclouders/web-client/src/helpers/resource/types'
import { AppNavigationItem } from '@ownclouders/web-pkg'
import { Store } from 'vuex'

// just a dummy function to trick gettext tools
function $gettext(msg) {
Expand All @@ -16,7 +17,13 @@ const appInfo = {
id: 'admin-settings',
icon: 'settings-4',
color: '#2b2b2b',
isFileEditor: false
isFileEditor: false,
applicationMenu: {
enabled: (store: Store<unknown>, ability: Ability) => {
return !!store.getters?.user?.id && ability.can('read-all', 'Setting')
},
priority: 40
}
}

const routes = ({ $ability }: { $ability: Ability }) => [
Expand Down
10 changes: 10 additions & 0 deletions packages/web-app-draw-io/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import { Resource } from '@ownclouders/web-client/src'
import { AppWrapperRoute } from '@ownclouders/web-pkg'
import translations from '../l10n/translations.json'
import App from './App.vue'
import { Store } from 'vuex'

const applicationId = 'draw-io'

Expand All @@ -26,6 +27,15 @@ const appInfo = {
name: 'Draw.io',
id: applicationId,
icon: 'grid',
color: '#EF6C00',
applicationMenu: {
enabled: (store: Store<unknown>) => {
return !!store.getters?.user?.id
},
priority: 30,
openAsEditor: true
},
defaultExtension: 'drawio',
extensions: [
{
extension: 'drawio',
Expand Down
6 changes: 5 additions & 1 deletion packages/web-app-files/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,11 @@ const appInfo = {
color: 'var(--oc-color-swatch-primary-muted)',
isFileEditor: false,
extensions: [],
fileSideBars
fileSideBars,
applicationMenu: {
enabled: () => true,
priority: 10
}
}
export const navItems = (context): AppNavigationItem[] => {
return [
Expand Down
10 changes: 10 additions & 0 deletions packages/web-app-text-editor/src/index.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import translations from '../l10n/translations.json'
import TextEditor from './App.vue'
import { AppWrapperRoute } from '@ownclouders/web-pkg'
import { Store } from 'vuex'

// just a dummy function to trick gettext tools
function $gettext(msg) {
Expand Down Expand Up @@ -92,7 +93,16 @@ const appInfo = {
name: $gettext('Text Editor'),
id: appId,
icon: 'file-text',
color: '#7b27b6',
isFileEditor: true,
applicationMenu: {
enabled: (store: Store<unknown>) => {
return !!store.getters?.user?.id
},
priority: 20,
openAsEditor: true
},
defaultExtension: 'txt',
extensions: fileExtensions().map((extensionItem) => {
return {
extension: extensionItem.extension,
Expand Down
10 changes: 5 additions & 5 deletions packages/web-client/src/helpers/space/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,11 +19,11 @@ export interface SpaceResource extends Resource {
getWebDavUrl({ path }: { path: string }): string
getWebDavTrashUrl({ path }: { path: string }): string
getDriveAliasAndItem(resource: Resource): string
isViewer(uuid: User): boolean
isEditor(uuid: User): boolean
isManager(uuid: User): boolean
isMember(uuid: User): boolean
isOwner(uuid: User): boolean
isViewer(user: User): boolean
isEditor(user: User): boolean
isManager(user: User): boolean
isMember(user: User): boolean
isOwner(user: User): boolean
}

export interface PersonalSpaceResource extends SpaceResource {
Expand Down
8 changes: 8 additions & 0 deletions packages/web-pkg/src/apps/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -52,14 +52,22 @@ export interface ApplicationQuickActions {

export type AppConfigObject = Record<string, any>

export interface ApplicationMenuItem {
enabled: () => boolean
priority: number
openAsEditor?: boolean
}

/** ApplicationInformation describes required information of an application */
export interface ApplicationInformation {
id?: string
name?: string
icon?: string
isFileEditor?: boolean
extensions?: any[]
defaultExtension?: string
fileSideBars?: any[]
applicationMenu?: ApplicationMenuItem
}

/**
Expand Down
47 changes: 44 additions & 3 deletions packages/web-pkg/src/components/AppTopBar.vue
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,13 @@
v-if="resource"
id="app-top-bar-resource"
:is-thumbnail-displayed="false"
:path-prefix="pathPrefix"
:resource="resource"
:parent-folder-name="parentFolderName"
:parent-folder-link-icon-additional-attributes="
parentFolderLinkIconAdditionalAttributes
"
:is-path-displayed="isPathDisplayed"
/>
</div>
<div class="oc-flex main-actions">
Expand Down Expand Up @@ -72,11 +78,13 @@
</template>

<script lang="ts">
import { computed, defineComponent, PropType } from 'vue'
import { computed, defineComponent, PropType, unref } from 'vue'
import { Resource } from '@ownclouders/web-client/src'
import { Action } from '../composables/actions/types'
import ContextActionMenu from './ContextActions/ContextActionMenu.vue'
import { useGettext } from 'vue3-gettext'
import { useFolderLink, useGetMatchingSpace } from '../composables'
import { isPublicSpaceResource, isShareSpaceResource } from '@ownclouders/web-client/src/helpers'
export default defineComponent({
name: 'AppTopBar',
Expand All @@ -98,15 +106,42 @@ export default defineComponent({
}
},
emits: ['close'],
setup() {
setup(props) {
const { $gettext } = useGettext()
const { getMatchingSpace } = useGetMatchingSpace()
const contextMenuLabel = computed(() => $gettext('Show context menu'))
const closeButtonLabel = computed(() => $gettext('Close'))
const { getParentFolderName, getParentFolderLinkIconAdditionalAttributes, getPathPrefix } =
useFolderLink()
const space = computed(() => getMatchingSpace(props.resource))
//FIXME: We currently have problems to display the parent folder name of a shared file, so we disabled it for now
const isPathDisplayed = computed(() => {
return !isShareSpaceResource(unref(space)) && !isPublicSpaceResource(unref(space))
})
const pathPrefix = computed(() => {
return props.resource ? getPathPrefix(props.resource) : null
})
const parentFolderName = computed(() => {
return props.resource ? getParentFolderName(props.resource) : null
})
const parentFolderLinkIconAdditionalAttributes = computed(() => {
return props.resource ? getParentFolderLinkIconAdditionalAttributes(props.resource) : null
})
return {
pathPrefix,
isPathDisplayed,
contextMenuLabel,
closeButtonLabel
closeButtonLabel,
parentFolderName,
parentFolderLinkIconAdditionalAttributes
}
}
})
Expand Down Expand Up @@ -139,6 +174,12 @@ export default defineComponent({
flex-basis: 250px;
margin: 0;
}
.oc-resource-indicators {
.text {
color: var(--oc-color-swatch-brand-contrast);
}
}
}
.open-file-bar {
Expand Down
Loading

0 comments on commit d8b2349

Please sign in to comment.