c++ - ejemplos - qt examples code
Qt 4.x: ¿cómo implementar arrastrar y soltar en el escritorio o en una carpeta? (3)
Creo que lo estás haciendo al revés.
No te importa a dónde va la gota, solo sabes que se dejó caer. En DropEvent, descargue el archivo en una ubicación temporal y luego configure los datos de mime para que sean lo que se descargó. Por supuesto, esto puede terminar con una segunda copia en el disco duro, será multiplataforma desde el principio. Es posible que pueda optimizarlo luego con llamadas específicas de la plataforma.
Eche un vistazo al ejemplo de Dropsite para ver cómo funcionan los datos de mime de otras fuentes ...
Editar:
Parece que el método de copia doble es el estándar si no escribe una extensión de shell (al menos para Windows). Filezilla y 7zip hacen eso, devuelven un tipo mime "text / uri-list" con una ubicación temporal. De esta manera, el explorador copia los datos de la ubicación temporal a la real. Su aplicación puede hacer lo mismo, crear un archivo temporal (o solo el nombre) sin datos. Utilizando el ejemplo de codificación retardada , cree los datos en la gota. Toda esta operación es muy específica de la plataforma que aparece. En Linux (ejecutando KDE) puedo arrastrar y soltar solo según el tipo mime. Parece que las ventanas no son tan flexibles.
He escrito una pequeña aplicación de transferencia de archivos escrita en C ++ utilizando Qt 4.x ... inicia sesión en un servidor, muestra al usuario una lista de archivos disponibles en el servidor y le permite cargar o descargar archivos.
Todo esto funciona bien; incluso puede arrastrar un archivo desde el escritorio (o desde una carpeta abierta), y cuando coloca el ícono del archivo en la vista de lista de archivos del servidor, el archivo eliminado se carga en el servidor.
Ahora también tengo una solicitud para la acción opuesta ... a mis usuarios les gustaría poder arrastrar un archivo fuera de la vista de lista de archivos del servidor y al escritorio, o en una ventana de carpeta abierta, y tener esa archivo descargado en esa ubicación.
Parece una solicitud razonable, pero no sé cómo implementarla. ¿Existe alguna forma para que una aplicación Qt encuentre el directorio correspondiente al lugar donde ocurrió el "evento de caída", cuando el icono se colocó en el escritorio o en una ventana de carpeta abierta? Idealmente, este sería un mecanismo neutral basado en Qt, pero si no existe, entonces serían suficientes los mecanismos específicos de la plataforma para MacOS / X y Windows (XP o superior).
¿Algunas ideas?
Solo implementas la parte de arrastre . No necesita saber dónde se produce la eliminación porque la aplicación que la recibe lo manejará y decidirá dónde almacenar su archivo.
Usted crea un QMimeData , no está seguro de qué tipo, pero por lo que vi here y here , tal vez "application / octet-stream" con su archivo como datos en un QByteArray o "text / uri-list" con url en su archivo.
Usted crea un QDrag y usa su método setMimeData () y exec () (no está seguro de qué QT :: DropAction elegir).
Aquí hay un ejemplo (disclamer: lo hice con color, no con archivos):
void DraggedWidget::mousePressEvent(QMouseEvent *event)
{
if (event->button() == Qt::LeftButton)
start_pos = event->pos();
}
void DraggedWidget::mouseMoveEvent(QMouseEvent *event)
{
if (event->buttons() & Qt::LeftButton) {
int distance = (event->pos() - start_pos).manhattanLength();
if (distance >= QApplication::startDragDistance())
{
/* Drag */
QMimeData *mime_data = new QMimeData;
mime_data->setData( ... );
QDrag *drag = new QDrag(this);
drag->setMimeData(mime_data);
drag->exec(Qt::CopyAction);
}
}
}
Lo siento, es bastante incompleto, espero que ayude un poco.
Mira a QMimeData
y su documentación, tiene una función virtual
virtual QVariant retrieveData ( const QString & mimetype, QVariant::Type type ) const
esto significa que debes arrastrar hacia el exterior para implementar estas funciones en consecuencia
class DeferredMimeData : public QMimeData
{
DeferredMimeData(QString downloadFilename) : m_filename(downloadFilename)
virtual QVariant retrieveData (const QString & mimetype, QVariant::Type type) const
{
if (mimetype matches expected && type matches expected)
{
perform download with m_filename
}
}
}
Los ejemplos de codificación retardada muestran este principio.
Es probable que también tenga que anular hasFormat
y los formats
para proporcionar los tipos adecuados, ya que la application/octet-stream
probablemente la que más le permita jugar, probablemente tendrá que leer cómo las ventanas manejan específicamente la función de arrastrar y soltar usando mime tipos
No sé cómo proporcionará el nombre del archivo con el que se guardó el archivo, pero probablemente tendrá que meterse en el lado de las ventanas de las cosas. Mirar la fuente de QWindowsMime
también podría ayudar. Podría haber un proceso de varios pasos en el que obtendrá solicitudes de datos de text/uri-list
para los nombres de archivo y luego application/octet-stream
para los datos.
Espero que esto ayude