Version: (using KDE KDE 3.5.0) Installed from: Gentoo Packages OS: Linux How to reproduce: * Open two konqueror windows. * In one of them, copy a file (CTRL-C) and close the window. * Now try to paste the copied file into the second konqueror window. This last action will attempt to paste a string, not a file. Konqueror (or Klipper, whatever is responsible) has forgotten that the copied object is a file.
Same here (r496940 on FreeBSD). I don't have klipper running, so presumably it isn't a klipper bug
It's a klipper limitation that it doesn't remember files, only text. If you don't run klipper, loosing copied text when exiting the source app is the expected behavior on X
SVN commit 504657 by lunakl: Handle urls (including application/x-kde-cutselection) as urls and not as text. BUG: 121114 M +3 -3 Makefile.am M +1 -1 historyimageitem.cpp M +3 -1 historyimageitem.h M +28 -7 historyitem.cpp M +6 -1 historyitem.h M +4 -2 historystringitem.h A historyurlitem.cpp [License: GPL (v2+)] A historyurlitem.h [License: GPL (v2+)] M +9 -14 toplevel.cpp --- trunk/KDE/kdebase/klipper/Makefile.am #504656:504657 @@ -8,15 +8,15 @@ CLEANFILES = dummy.cpp -libklipper_common_la_LIBADD = $(LIB_KDEUI) $(LIB_KSYCOCA) $(LIB_XFIXES) +libklipper_common_la_LIBADD = $(LIB_KDEUI) $(LIB_KSYCOCA) $(LIB_XFIXES) -lkde3support libklipper_common_la_SOURCES = main.cpp toplevel.cpp urlgrabber.cpp configdialog.cpp \ toplevel.skel clipboardpoll.cpp history.cpp historyitem.cpp historystringitem.cpp klipperpopup.cpp popupproxy.cpp \ - historyimageitem.cpp + historyimageitem.cpp historyurlitem.cpp libklipper_common_la_METASOURCES = AUTO libklipper_common_la_LDFLAGS = $(all_libraries) -klipper_la_LIBADD = libklipper_common.la +klipper_la_LIBADD = libklipper_common.la klipper_la_SOURCES = dummy.cpp klipper_la_LDFLAGS = $(all_libraries) -module -avoid-version --- trunk/KDE/kdebase/klipper/historyimageitem.cpp #504656:504657 @@ -31,7 +31,7 @@ { } -const QString& HistoryImageItem::text() const { +QString HistoryImageItem::text() const { if ( m_text.isNull() ) { m_text = QString( "%1x%2x%3 %4" ) .arg( m_data.width() ) --- trunk/KDE/kdebase/klipper/historyimageitem.h #504656:504657 @@ -23,6 +23,7 @@ #include "historyitem.h" #include <qpixmap.h> +#include <q3dragobject.h> /** * A image entry in the clipboard history. @@ -32,7 +33,7 @@ public: HistoryImageItem( const QPixmap& data ); virtual ~HistoryImageItem() {} - virtual const QString& text() const; + virtual QString text() const; virtual bool operator==( const HistoryItem& rhs) const { if ( const HistoryImageItem* casted_rhs = dynamic_cast<const HistoryImageItem*>( &rhs ) ) { return &casted_rhs->m_data == &m_data; // Not perfect, but better than nothing. @@ -40,6 +41,7 @@ return false; } virtual const QPixmap& image() const { return m_data; } + virtual QMimeSource* mimeSource() const { return new Q3ImageDrag( m_data.convertToImage()) ; } virtual void write( QDataStream& stream ) const; --- trunk/KDE/kdebase/klipper/historyitem.cpp #504656:504657 @@ -19,14 +19,17 @@ */ #include <qmime.h> #include <q3dragobject.h> +#include <qmap.h> #include <qstring.h> #include <qpixmap.h> #include <kdebug.h> +#include <k3urldrag.h> #include "historyitem.h" #include "historystringitem.h" #include "historyimageitem.h" +#include "historyurlitem.h" HistoryItem::HistoryItem() { @@ -44,18 +47,27 @@ kdDebug() << "format(" << i <<"): " << f << endl; } #endif + if( K3URLDrag::canDecode( &aSource )) { + KURL::List urls; + QMap<QString,QString> metaData; + if( K3URLDrag::decode( &aSource, urls, metaData )) { + // this is from KonqDrag (libkonq) + QByteArray a = aSource.encodedData( "application/x-kde-cutselection" ); + bool cut = !a.isEmpty() && (a.at(0) == '1'); // true if 1 + return new HistoryURLItem( urls, metaData, cut ); + } + } if ( Q3TextDrag::canDecode( &aSource ) ) { QString text; - Q3TextDrag::decode( &aSource, text ); - return text.isNull() ? 0 : new HistoryStringItem( text ); - } else if ( Q3ImageDrag::canDecode( &aSource ) ) { + if( Q3TextDrag::decode( &aSource, text )) + return text.isNull() ? 0 : new HistoryStringItem( text ); + } + if ( Q3ImageDrag::canDecode( &aSource ) ) { QPixmap image; - Q3ImageDrag::decode( &aSource, image ); - return image.isNull() ? 0 : new HistoryImageItem( image ); + if( Q3ImageDrag::decode( &aSource, image )) + return image.isNull() ? 0 : new HistoryImageItem( image ); } - return 0; // Failed. - } HistoryItem* HistoryItem::create( QDataStream& aSource ) { @@ -64,6 +76,15 @@ } QString type; aSource >> type; + if ( type == "url" ) { + KURL::List urls; + QMap< QString, QString > metaData; + int cut; + aSource >> urls; + aSource >> metaData; + aSource >> cut; + return new HistoryURLItem( urls, metaData, cut ); + } if ( type == "string" ) { QString text; aSource >> text; --- trunk/KDE/kdebase/klipper/historyitem.h #504656:504657 @@ -39,7 +39,7 @@ * An image would be returned as a descriptive * text, such as 32x43 image. */ - virtual const QString& text() const = 0; + virtual QString text() const = 0; /** * Return the current item as text @@ -49,6 +49,11 @@ inline virtual const QPixmap& image() const; /** + * Returns QMimeSource suitable for QClipboard::setData(). + */ + virtual QMimeSource* mimeSource() const = 0; + + /** * Write object on datastream */ virtual void write( QDataStream& stream ) const = 0; --- trunk/KDE/kdebase/klipper/historystringitem.h #504656:504657 @@ -21,6 +21,7 @@ #define _HISTORYSTRINGITEM_H_ #include <qstring.h> +#include <q3dragobject.h> #include "historyitem.h" @@ -32,13 +33,14 @@ public: HistoryStringItem( const QString& data ); virtual ~HistoryStringItem() {} - virtual const QString& text() const; + virtual QString text() const; virtual bool operator==( const HistoryItem& rhs) const { if ( const HistoryStringItem* casted_rhs = dynamic_cast<const HistoryStringItem*>( &rhs ) ) { return casted_rhs->m_data == m_data; } return false; } + virtual QMimeSource* mimeSource() const { return new Q3TextDrag( m_data ) ; } /** * Write object on datastream @@ -49,7 +51,7 @@ QString m_data; }; -inline const QString& HistoryStringItem::text() const { return m_data; } +inline QString HistoryStringItem::text() const { return m_data; } #endif --- trunk/KDE/kdebase/klipper/toplevel.cpp #504656:504657 @@ -49,6 +49,7 @@ #include <ksimpleconfig.h> #include <kstringhandler.h> #include <ksystemtray.h> +#include <kurldrag.h> #include <kwin.h> #include <kdebug.h> #include <kglobalsettings.h> @@ -877,13 +878,15 @@ #ifdef __GNUC__ #warning This should be maybe extended for KDE4 or at least get a checkbox somewhere in UI #endif -// Limit mimetypes that are tracked by Klipper (this is basically a workaround -// for #109032). Can't add UI in 3.5 because of string freeze, and I'm not sure -// if this actually needs to be more configurable than only text vs all klipper knows. - if( Q3TextDrag::canDecode( data )) + if( KURLDrag::canDecode( data )) ; // ok + else if( Q3TextDrag::canDecode( data )) + ; // ok else if( Q3ImageDrag::canDecode( data )) { +// Limit mimetypes that are tracked by Klipper (this is basically a workaround +// for #109032). Can't add UI in 3.5 because of string freeze, and I'm not sure +// if this actually needs to be more configurable than only text vs all klipper knows. if( bIgnoreImages ) return; else @@ -950,11 +953,7 @@ #ifdef NOSIY_KLIPPER kdDebug() << "Setting selection to <" << item.text() << ">" << endl; #endif - if ( item.image().isNull() ) { - clip->setText( item.text(), QClipboard::Selection ); - } else { - clip->setPixmap( item.image(), QClipboard::Selection ); - } + clip->setData( item.mimeSource(), QClipboard::Selection ); #if 0 m_lastSelection = clip->data()->serialNumber();< #endif @@ -963,11 +962,7 @@ #ifdef NOSIY_KLIPPER kdDebug() << "Setting clipboard to <" << item.text() << ">" << endl; #endif - if ( item.image().isNull() ) { - clip->setText( item.text(), QClipboard::Clipboard ); - } else { - clip->setPixmap( item.image(), QClipboard::Clipboard ); - } + clip->setData( item.mimeSource(), QClipboard::Clipboard ); #if 0 m_lastClipboard = clip->data()->serialNumber(); #endif
Wow, that was fast.... Thanks!