mirror of
https://github.com/lights0123/n-link.git
synced 2026-08-08 02:33:28 +00:00
feat(core): port CalcInfo and FileView to Vue 3 script setup
This commit is contained in:
parent
7869a747bc
commit
3ee9925f91
|
|
@ -31,7 +31,7 @@
|
|||
</div>
|
||||
</button>
|
||||
<button class="mt-4 button gray-button"
|
||||
@click="nativeUpload ? $refs.upload.click() : $devices.uploadOs(dev, info.os_extension.split('.').pop())">
|
||||
@click="nativeUpload ? upload?.click() : $devices.uploadOs(dev, info.os_extension.split('.').pop())">
|
||||
Upload OS
|
||||
</button>
|
||||
<input v-if="nativeUpload" ref="upload" type="file" class="hidden" :accept="info.os_extension"
|
||||
|
|
@ -39,40 +39,45 @@
|
|||
</div>
|
||||
</template>
|
||||
|
||||
<script lang="ts">
|
||||
import {Component, Prop, Vue} from 'vue-property-decorator';
|
||||
import type {Info, Version} from './devices';
|
||||
import fileSize from "filesize";
|
||||
<script setup lang="ts">
|
||||
import {inject, ref} from 'vue';
|
||||
import {DEVICES_KEY, type GenericDevices, type Info, type Version} from './devices';
|
||||
import {filesize} from 'filesize';
|
||||
|
||||
@Component
|
||||
export default class FileView extends Vue {
|
||||
@Prop({type: Object, required: true}) private info!: Info;
|
||||
@Prop({type: String, required: true}) private dev!: string;
|
||||
@Prop({type: Boolean, default: false}) private nativeUpload!: boolean;
|
||||
refreshing = false;
|
||||
const props = withDefaults(defineProps<{
|
||||
info: Info;
|
||||
dev: string;
|
||||
nativeUpload?: boolean;
|
||||
}>(), {
|
||||
nativeUpload: false,
|
||||
});
|
||||
|
||||
formatSize(size: number) {
|
||||
return fileSize(size, {round: 1});
|
||||
const devices = inject(DEVICES_KEY) as GenericDevices;
|
||||
|
||||
const refreshing = ref(false);
|
||||
const upload = ref<HTMLInputElement | null>(null);
|
||||
|
||||
function formatSize(size: number) {
|
||||
return filesize(size, {round: 1});
|
||||
}
|
||||
|
||||
function formatVersion(version: Version) {
|
||||
return `${version.major}.${version.minor}.${version.patch}.${version.build}`;
|
||||
}
|
||||
|
||||
async function refresh() {
|
||||
refreshing.value = true;
|
||||
try {
|
||||
await devices.update(props.dev);
|
||||
} catch (e) {
|
||||
/* */
|
||||
}
|
||||
refreshing.value = false;
|
||||
}
|
||||
|
||||
formatVersion(version: Version) {
|
||||
return `${version.major}.${version.minor}.${version.patch}.${version.build}`;
|
||||
}
|
||||
|
||||
async refresh() {
|
||||
this.refreshing = true;
|
||||
try {
|
||||
await this.$devices.update(this.dev);
|
||||
} catch (e) {
|
||||
/* */
|
||||
}
|
||||
this.refreshing = false;
|
||||
}
|
||||
|
||||
uploadNative(e: Event & { target: HTMLInputElement }) {
|
||||
const file = e.target.files?.[0];
|
||||
if (file) this.$devices.uploadOsFile(this.dev, file);
|
||||
}
|
||||
function uploadNative(e: Event & { target: HTMLInputElement }) {
|
||||
const file = e.target.files?.[0];
|
||||
if (file) devices.uploadOsFile(props.dev, file);
|
||||
}
|
||||
</script>
|
||||
|
||||
|
|
|
|||
|
|
@ -10,55 +10,59 @@
|
|||
</div>
|
||||
</template>
|
||||
|
||||
<script lang="ts">
|
||||
import {Component, Prop, Vue, Watch} from 'vue-property-decorator';
|
||||
<script setup lang="ts">
|
||||
import {computed, ref, watch} from 'vue';
|
||||
import type {FileInfo} from './devices';
|
||||
import FileIcon from "./FileIcon.vue";
|
||||
import FileIcon from './FileIcon.vue';
|
||||
|
||||
@Component({
|
||||
components: {FileIcon}
|
||||
})
|
||||
export default class FileView extends Vue {
|
||||
@Prop({type: Array, default: () => ([])}) private files!: FileInfo[];
|
||||
@Prop({type: Boolean, default: false}) private showHidden!: boolean;
|
||||
selected: number[] = [];
|
||||
const props = withDefaults(defineProps<{
|
||||
files: FileInfo[];
|
||||
showHidden?: boolean;
|
||||
}>(), {
|
||||
files: () => [],
|
||||
showHidden: false,
|
||||
});
|
||||
|
||||
@Watch('selected', {deep: true, immediate: true})
|
||||
onSelect(selected: number[]) {
|
||||
this.$emit('select', selected.map(file => this.filteredFiles[file]));
|
||||
const emit = defineEmits<{
|
||||
nav: [path: string];
|
||||
select: [files: FileInfo[]];
|
||||
}>();
|
||||
|
||||
const selected = ref<number[]>([]);
|
||||
|
||||
const filteredFiles = computed(() => {
|
||||
if (props.showHidden) return props.files;
|
||||
return props.files.filter(file => file.isDir || file.path.endsWith('.tns'));
|
||||
});
|
||||
|
||||
watch(selected, (sel) => {
|
||||
emit('select', sel.map(file => filteredFiles.value[file]));
|
||||
}, {deep: true, immediate: true});
|
||||
|
||||
watch(() => props.files, () => {
|
||||
selected.value = [];
|
||||
});
|
||||
|
||||
function formatPath({path, isDir}: FileInfo) {
|
||||
const name = path.split('/').pop() as string;
|
||||
if (props.showHidden || isDir) return name;
|
||||
return name.substring(0, name.length - 4);
|
||||
}
|
||||
|
||||
function xorSelection(i: number) {
|
||||
if (selected.value.includes(i)) selected.value = selected.value.filter(num => num !== i);
|
||||
else selected.value.push(i);
|
||||
}
|
||||
|
||||
function shiftSelection(item: number) {
|
||||
const lastSelected = selected.value[selected.value.length - 1];
|
||||
if (lastSelected === undefined) {
|
||||
selected.value.push(item);
|
||||
return;
|
||||
}
|
||||
|
||||
@Watch('files')
|
||||
onFileChange() {
|
||||
this.selected = [];
|
||||
}
|
||||
|
||||
get filteredFiles() {
|
||||
if (this.showHidden) return this.files;
|
||||
return this.files.filter(file => file.isDir || file.path.endsWith('.tns'));
|
||||
}
|
||||
|
||||
formatPath({path, isDir}: FileInfo) {
|
||||
const name = path.split('/').pop() as string;
|
||||
if (this.showHidden || isDir) return name;
|
||||
return name.substring(0, name.length - 4);
|
||||
}
|
||||
|
||||
xorSelection(i: number) {
|
||||
if (this.selected.includes(i)) this.selected = this.selected.filter(num => num !== i);
|
||||
else this.selected.push(i);
|
||||
}
|
||||
|
||||
shiftSelection(item: number) {
|
||||
const lastSelected = this.selected[this.selected.length-1];
|
||||
if(lastSelected === undefined) {
|
||||
this.selected.push(item);
|
||||
return;
|
||||
}
|
||||
const [lower, upper] = item > lastSelected ? [lastSelected, item] : [item, lastSelected];
|
||||
for(let i = lower; i <= upper; i++) {
|
||||
if (!this.selected.includes(i))this.selected.push(i);
|
||||
}
|
||||
const [lower, upper] = item > lastSelected ? [lastSelected, item] : [item, lastSelected];
|
||||
for (let i = lower; i <= upper; i++) {
|
||||
if (!selected.value.includes(i)) selected.value.push(i);
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
|
|
|||
Loading…
Reference in a new issue