able to receive file

This commit is contained in:
2026-04-27 15:06:59 +08:00
parent 5442e32abc
commit 71ea3dbd01
11 changed files with 605 additions and 32 deletions

View File

@@ -1,6 +1,7 @@
import QtQuick
import QtQuick.Controls
import QtQuick.Layouts
import QtQuick.Dialogs
ApplicationWindow {
id: root
@@ -9,6 +10,12 @@ ApplicationWindow {
height: 600
title: qsTr("LocalSend")
property string currentSessionId: ""
property var currentFiles: []
property string currentSenderAlias: ""
property string currentSenderIp: ""
property var receiveProgress: ({})
StackView {
id: stackView
anchors.fill: parent
@@ -18,6 +25,174 @@ ApplicationWindow {
}
}
Dialog {
id: receiveDialog
anchors.centerIn: parent
modal: true
closePolicy: Popup.NoAutoClose
standardButtons: Dialog.Ok | Dialog.Cancel
title: qsTr("Receive Files")
onAccepted: {
appController.acceptReceive(currentSessionId)
currentSessionId = ""
}
onRejected: {
appController.declineReceive(currentSessionId)
currentSessionId = ""
}
ColumnLayout {
spacing: 12
Label {
text: qsTr("From: %1 (%2)").arg(currentSenderAlias).arg(currentSenderIp)
font.bold: true
}
Label {
text: qsTr("Files:")
}
ListView {
Layout.fillWidth: true
Layout.preferredHeight: Math.min(200, contentHeight)
width: 400
model: currentFiles
spacing: 4
delegate: RowLayout {
width: ListView.view.width
spacing: 8
Label {
text: modelData.fileName
Layout.fillWidth: true
elide: Text.ElideMiddle
}
Label {
text: formatSize(modelData.size)
color: "gray"
}
}
}
Label {
text: qsTr("Save to: %1").arg(appController.downloadPath)
color: palette.mid
font.pixelSize: 12
}
}
}
Dialog {
id: progressDialog
anchors.centerIn: parent
modal: true
closePolicy: Popup.NoAutoClose
title: qsTr("Receiving Files")
ColumnLayout {
spacing: 12
Label {
id: progressLabel
text: qsTr("Receiving from %1...").arg(currentSenderAlias)
}
ProgressBar {
id: totalProgressBar
Layout.fillWidth: true
from: 0
to: 100
value: calculateTotalProgress()
}
Label {
text: qsTr("%1% complete").arg(Math.round(totalProgressBar.value))
color: "gray"
}
}
property var progressData: ({})
}
Connections {
target: appController
function onReceiveRequest(sessionId, senderAlias, senderIp, files) {
currentSessionId = sessionId
currentSenderAlias = senderAlias
currentSenderIp = senderIp
currentFiles = files
if (appController.quickSave) {
appController.acceptReceive(sessionId)
} else {
receiveDialog.open()
}
}
function onReceiveProgress(sessionId, fileId, progress) {
if (sessionId === currentSessionId) {
receiveProgress[fileId] = progress
receiveProgress = Object.assign({}, receiveProgress)
progressDialog.progressData = receiveProgress
}
}
function onReceiveCompleted(sessionId) {
if (sessionId === currentSessionId) {
progressDialog.close()
receiveProgress = {}
currentSessionId = ""
}
}
function onReceiveError(sessionId, error) {
if (sessionId === currentSessionId) {
progressDialog.close()
errorDialog.text = error
errorDialog.open()
}
}
}
Dialog {
id: errorDialog
anchors.centerIn: parent
modal: true
standardButtons: Dialog.Ok
title: qsTr("Error")
property alias text: errorLabel.text
Label {
id: errorLabel
}
}
function formatSize(bytes) {
if (bytes < 1024) return bytes + " B"
if (bytes < 1024 * 1024) return (bytes / 1024).toFixed(1) + " KB"
if (bytes < 1024 * 1024 * 1024) return (bytes / (1024 * 1024)).toFixed(1) + " MB"
return (bytes / (1024 * 1024 * 1024)).toFixed(2) + " GB"
}
function calculateTotalProgress() {
if (!currentFiles || currentFiles.length === 0) return 0
var total = 0
var count = 0
for (var i = 0; i < currentFiles.length; i++) {
var fileId = currentFiles[i].id
if (receiveProgress[fileId] !== undefined) {
total += receiveProgress[fileId] * 100
count++
}
}
return count > 0 ? total / currentFiles.length : 0
}
Component {
id: homePageComponent
Page {
@@ -90,7 +265,7 @@ ApplicationWindow {
Button {
text: qsTr("Send")
onClicked: {
// send to this device
// TODO: send to this device
}
}
}
@@ -106,7 +281,7 @@ ApplicationWindow {
Item { Layout.fillWidth: true }
Label {
text: qsTr("Alias: %1").arg(appController.alias)
color: "gray"
color: palette.mid
}
}
}
@@ -162,6 +337,36 @@ ApplicationWindow {
to: 65535
onValueChanged: appController.port = value
}
Label { text: qsTr("Download Path:") }
RowLayout {
Layout.fillWidth: true
TextField {
id: downloadPathField
text: appController.downloadPath
onEditingFinished: appController.downloadPath = text
Layout.fillWidth: true
}
Button {
text: qsTr("Browse")
onClicked: folderDialog.open()
}
}
Label { text: qsTr("Quick Save:") }
CheckBox {
id: quickSaveCheck
checked: appController.quickSave
onCheckedChanged: appController.quickSave = checked
}
}
FolderDialog {
id: folderDialog
onAccepted: {
downloadPathField.text = selectedFolder.toString().replace("file://", "")
appController.downloadPath = downloadPathField.text
}
}
Item { Layout.fillHeight: true }