Bug 104347

Summary: window width is widened automatically when the status bar needs more room
Product: [Applications] kst Reporter: Matthew Truch <matt>
Component: uiAssignee: kst
Status: RESOLVED FIXED    
Severity: normal    
Priority: NOR    
Version: 1.x   
Target Milestone: ---   
Platform: Slackware   
OS: Linux   
Latest Commit: Version Fixed In:
Sentry Crash Report:

Description Matthew Truch 2005-04-22 01:28:22 UTC
Version:           1.1.0_beta1 (using KDE KDE 3.3.0)
Installed from:    Slackware Packages
OS:                Linux

How to reproduce:

Open a kst window that is narrow(ish).
Do something that generates more text in the status bar (ie move the mouse into a plot, or turn on cursor mode by pressing 'c').  
Watch the window self-widen.  

Expected behavior: The window doesn't get wider, but something visual indicates the missing info on the side (like the >> that appears in the toolbar when the window is too narrow). It would be best if the text in the status bar has a priority so that the first thing to disappear is the 'Ready', the last the cursors/position info.
Comment 1 George Staikos 2005-04-22 02:56:42 UTC
This is very much [Q|K]StatusBar behaviour.  I'm not sure it's a good idea to 
try to hack around it.  However, the obvious solution is to use a 
KSqueezedTextLabel.  I'll post a patch for this but I won't include it in 
1.1.0.
Comment 2 Andrew Walker 2005-07-21 00:34:10 UTC
Of the apps I tested (Firefox, Qt Designer, Task Scheduler) none of them will resize the window just because the status bar does not have room to display all the text in the status bar. Firefox displays the text terminated with ellipsis when necessary.
Comment 3 George Staikos 2005-07-21 00:58:42 UTC
Right, that's what KSqueezedTextLabel does.  I guess I should make that patch one day.. or you can if you like. :-)
Comment 4 Andrew Walker 2005-07-22 20:19:18 UTC
SVN commit 437686 by arwalker:

BUG:104347 Prevent changes to the status bar text making the main window enlarge in size.

 M  +1 -0      Makefile.am  
 M  +85 -6     kst.cpp  
 M  +7 -2      kst.h  
 A             statuslabel.cpp   [License: GPL (v2+)]
 A             statuslabel.h   [License: GPL (v2+)]


--- trunk/extragear/graphics/kst/kst/Makefile.am #437685:437686
@@ -125,6 +125,7 @@
 	kstiface_impl.cpp \
 	kstcombobox.cpp \
 	draggablelistbox.cpp \
+	statuslabel.cpp \
 	plotlistbox.cpp \
 	plotmimesource.cpp \
 	kstplotdrag.cpp \
--- trunk/extragear/graphics/kst/kst/kst.cpp #437685:437686
@@ -82,6 +82,7 @@
 #include "plotmimesource.h"
 #include "pluginmanager.h"
 #include "psversion.h"
+#include "statuslabel.h"
 #include "sysinfo.h"
 #include "updatethread.h"
 #include "vectorsavedialog.h"
@@ -834,10 +835,12 @@
 
 
 void KstApp::initStatusBar() {
-  _dataBar = new QLabel(QString::null, statusBar());
+  _dataBar = new StatusLabel(QString::null, statusBar());
+  _dataBar->setTextFormat(Qt::PlainText);
   statusBar()->addWidget(_dataBar, 5, true);
 
-  _readyBar = new QLabel(i18n("Almost Ready"), statusBar());
+  _readyBar = new StatusLabel(i18n("Almost Ready"), statusBar());
+  _readyBar->setTextFormat(Qt::PlainText);
   _readyBar->setAlignment(Qt::AlignRight | Qt::AlignVCenter);
   statusBar()->addWidget(_readyBar, 5, true);
 
@@ -849,14 +852,18 @@
   _progressBar->hide();
 
 #ifdef HAVE_LINUX
-  _memoryBar = new QLabel(i18n("0 MB available"), statusBar());
+  _memoryBar = new StatusLabel(i18n("0 MB available"), statusBar());
+  _memoryBar->setTextFormat(Qt::PlainText);
   statusBar()->addWidget(_memoryBar, 0, true);
   connect(&_memTimer, SIGNAL(timeout()), this, SLOT(updateMemoryStatus()));
   _memTimer.start(5000);
 #endif
 
   statusBar()->show();
+  
+  slotUpdateMemoryMsg(i18n("0 MB available"));
   slotUpdateStatusMsg(i18n("Ready"));
+  slotUpdateDataMsg(i18n(""));
 }
 
 void KstApp::initDocument() {
@@ -1531,26 +1538,96 @@
 void KstApp::slotViewStatusBar() {
   if (StatusBarAction->isChecked()) {
     statusBar()->show();
+    updateStatusBarText();
   } else {
     statusBar()->hide();
   }
 }
 
+void KstApp::updateStatusBarText() {
+  if (statusBar()->isShown()) {
+    QFontMetrics fm(fontMetrics());
+    int widthUsed;
+    int margin = 3;
+    int spacing = 6;
+    int widthCurrent = statusBar()->width();
+    int widthAvailable = widthCurrent - (2*margin) - spacing;
+    int widthData = fm.width(_dataBar->fullText());
+    int widthReady = fm.width(_readyBar->fullText());
+    
+    if (_progressBar->isShown()) {
+      widthAvailable -= _progressBar->width();
+      widthAvailable -= spacing;
+    }
+    
+    widthUsed  = widthData;
+    widthUsed += widthReady;
+#ifdef HAVE_LINUX
+    widthUsed += fm.width(_memoryBar->fullText());
+    widthAvailable -= spacing;
+#endif
 
+    if (widthUsed > widthAvailable) {
+      if (widthData < widthAvailable) {       
+        statusBar()->setMaximumWidth(widthCurrent);
+
+#ifdef HAVE_LINUX
+        if ((widthAvailable - widthData)/2 > widthReady) {
+          _memoryBar->setTextWidth(fm, widthAvailable - widthData - widthReady);
+          _readyBar->setTextWidth(fm, widthReady);          
+        } else {
+          _memoryBar->setTextWidth(fm, (widthAvailable - widthData)/2);
+          _readyBar->setTextWidth(fm, (widthAvailable - widthData)/2);
+        }
+#else
+        _readyBar->setTextWidth(fm, widthAvailable - widthData);        
+#endif
+        _dataBar->setTextWidth(fm, widthData);        
+        
+        statusBar()->setMaximumWidth(32767);
+      } else {
+#ifdef HAVE_LINUX
+        _memoryBar->setTextWidth(fm, 0);
+#endif        
+        _readyBar->setTextWidth(fm, 0);
+        _dataBar->setTextWidth(fm, widthAvailable);
+      }
+    } else {
+#ifdef HAVE_LINUX
+      _memoryBar->setFullText();
+#endif
+      _readyBar->setFullText();
+      _dataBar->setFullText();
+    }
+  }  
+}
+
+
 void KstApp::slotUpdateStatusMsg(const QString& msg) {
-  _readyBar->setText(msg);
+  _readyBar->setFullText( msg );
+  updateStatusBarText();
 }
 
 
 void KstApp::slotUpdateDataMsg(const QString& msg) {
-  _dataBar->setText(msg);
+  _dataBar->setFullText( msg );
+  updateStatusBarText();
 }
 
 
+void KstApp::slotUpdateMemoryMsg(const QString& msg) {
+#ifdef HAVE_LINUX
+  _memoryBar->setFullText( msg );
+  updateStatusBarText();
+#endif
+}
+
+
 void KstApp::slotUpdateProgress(int total, int step, const QString &msg) {
   if (step == 0 && msg.isNull()) {
     slotUpdateStatusMsg(i18n("Ready"));
     _progressBar->hide();
+    updateStatusBarText();
     return;
   }
 
@@ -1575,6 +1652,8 @@
   } else {
     slotUpdateStatusMsg(msg);
   }
+  
+  updateStatusBarText();
 
   kapp->eventLoop()->processEvents(QEventLoop::ExcludeSocketNotifiers, 10);
 }
@@ -2162,7 +2241,7 @@
 #ifdef HAVE_LINUX
   meminfo();
   unsigned long mi = S(kb_main_free + kb_main_buffers + kb_main_cached);
-  _memoryBar->setText(i18n("%1 MB available").arg(mi / (1024 * 1024)));
+  slotUpdateMemoryMsg(i18n("%1 MB available").arg(mi / (1024 * 1024)));
 #endif
 }
 
--- trunk/extragear/graphics/kst/kst/kst.h #437685:437686
@@ -29,6 +29,7 @@
 // application specific includes
 #include "kst2dplot.h"
 #include "ksteventmonitorentry.h"
+//#include "statuslabel.h"
 
 enum LegendType { LegendOn, LegendOff, LegendAuto };
 enum DataType { DataOnly, DataPSD, PSDOnly };
@@ -55,6 +56,7 @@
 class KstViewMatricesDialogI;
 class KstViewFitsDialogI;
 class KstQuickStartDialogI;
+class StatusLabel;
 class UpdateThread;
 class VectorSaveDialog;
 
@@ -265,8 +267,10 @@
     void slotViewStatusBar();
 
     /** changes the statusbar contents */
+    void updateStatusBarText();
     void slotUpdateStatusMsg(const QString &msg);
     void slotUpdateDataMsg(const QString &msg);
+    void slotUpdateMemoryMsg(const QString &msg);
     void slotUpdateProgress(int total, int step, const QString &msg);
 
     /** just calls plotDialog->show_I(0) */
@@ -515,9 +519,10 @@
     KRadioAction *_gfxPolylineAction;
     KRadioAction *_gfxLabelAction;
     
-    QLabel *_readyBar;
+    StatusLabel *_readyBar;
+    StatusLabel *_memoryBar;
+    StatusLabel *_dataBar;
     KProgress *_progressBar;
-    QLabel *_memoryBar, *_dataBar;
     bool _stopping;
     KstIfaceImpl *_dcopIface;
     UpdateThread *_updateThread;