Bo Peng wrote:
> Hi, Peter,
> 
> I revised your patch and now it works fine (save restore on/off and

Nice improvements! I feared the casts.

> location). It works like this. The major problem is with
> math/review/table toolbars. The logic is now:
> 
> 1. if math is on when lyx exists, I assume it is always on
> 2. if math is off when lyx exists, I assume it is auto.

But now it does not remember the position of the moved auto toolbars.
It does also not remember that I've manually enabled a auto toolbar,
shouldn't it then in the next session also be visible after loading?


> Now, we need to change lyx's behavior. Right now, "turn on math" is
> not "always on". The math toolbar will disappear if I click on text.
> 
> JMarc, can I apply?
> Bo
> 
> 
> ------------------------------------------------------------------------
> 
> Index: src/session.C
> ===================================================================
> --- src/session.C     (revision 15675)
> +++ src/session.C     (working copy)
> @@ -48,6 +48,7 @@
>  string const sec_lastopened = "[last opened files]";
>  string const sec_bookmarks = "[bookmarks]";
>  string const sec_session = "[session info]";
> +string const sec_toolbars = "[toolbars]";
>  
>  } // anon namespace
>  
> @@ -267,6 +268,51 @@
>  }
>  
>  
> +void ToolbarSection::read(istream & is)
> +{
> +     string tmp;
> +     do {
> +             char c = is.peek();
> +             if (c == '[')
> +                     break;
> +             getline(is, tmp);
> +
> +             // Read session info, saved as key/value pairs
> +             // would better yell if pos returns npos
> +             string::size_type pos = tmp.find_first_of(" = ");
> +             // silently ignore lines without " = "
> +             if (pos != string::npos) {
> +                     string key = tmp.substr(0, pos);
> +                     bool visible;
> +                     int location;
> +                     istringstream value(tmp.substr(pos + 3));
> +                     value >> visible;
> +                     value.ignore(1); // ignore " "
> +                     value >> location;
> +                     toolbars[key] = ToolbarInfo(visible, location);
> +             }
> +     } while (is.good());
> +}
> +
> +
> +void ToolbarSection::write(ostream & os) const
> +{
> +     os << '\n' << sec_toolbars << '\n';
> +     for (ToolbarMap::const_iterator tb = toolbars.begin();
> +             tb != toolbars.end(); ++tb) {
> +             os << tb->first << " = "
> +               << tb->second.visible << " "
> +               << tb->second.location << '\n';
> +     }
> +}
> +
> +
> +ToolbarSection::ToolbarInfo & ToolbarSection::load(string const & name)
> +{
> +     return toolbars[name];
> +}
> +
> +
>  void SessionInfoSection::read(istream & is)
>  {
>       string tmp;
> @@ -349,6 +395,8 @@
>                       lastFilePos().read(is);
>               else if (tmp == sec_bookmarks)
>                       bookmarks().read(is);
> +             else if (tmp == sec_toolbars)
> +                     toolbars().read(is);
>               else if (tmp == sec_session)
>                       sessionInfo().read(is);
>               else
> @@ -368,6 +416,7 @@
>               lastOpened().write(os);
>               lastFilePos().write(os);
>               bookmarks().write(os);
> +             toolbars().write(os);
>               sessionInfo().write(os);
>       } else
>               lyxerr << "LyX: Warning: unable to save Session: "
> Index: src/frontends/Toolbars.C
> ===================================================================
> --- src/frontends/Toolbars.C  (revision 15675)
> +++ src/frontends/Toolbars.C  (working copy)
> @@ -37,14 +37,77 @@
>  {}
>  
>  
> +void Toolbars::initFlags(ToolbarBackend::Toolbar & tbb)
> +{
> +     ToolbarSection::ToolbarInfo & info = 
> LyX::ref().session().toolbars().load(tbb.name);
> +
> +     unsigned int flags = static_cast<int>(tbb.flags);

Much better than my solution ;)

> +     // remove position
> +     unsigned int clean = ~ (ToolbarBackend::TOP | ToolbarBackend::BOTTOM
> +                             | ToolbarBackend::RIGHT | ToolbarBackend::LEFT);
> +
> +     bool valid_location = true;
> +     // init tbb.flags with saved location
> +     if (info.location == ToolbarSection::ToolbarInfo::top)
> +             flags = flags & clean | ToolbarBackend::TOP;
> +     else if (info.location == ToolbarSection::ToolbarInfo::bottom)
> +             flags = flags & clean | ToolbarBackend::BOTTOM;
> +     else if (info.location == ToolbarSection::ToolbarInfo::right)
> +             flags = flags & clean | ToolbarBackend::RIGHT;
> +     else if (info.location == ToolbarSection::ToolbarInfo::left)
> +             flags = flags & clean | ToolbarBackend::LEFT;
> +     else
> +             valid_location = false;
> +
> +     // invalid location is for a new toolbar that has no saved information,
> +     // so info.visible is not used for this case.
> +     if (valid_location) {
> +             // init tbb.flags with saved visibility,
> +             if (info.visible) {
> +                     // if visible, all toolbars are set to ON, even for 
> math etc
> +                     // clear one bit
> +                     flags &= ~ToolbarBackend::OFF;
> +                     // and set another
> +                     flags |= ToolbarBackend::ON;
> +             } else if((flags & ToolbarBackend::MATH) || (flags & 
> ToolbarBackend::REVIEW) || (flags & ToolbarBackend::TABLE)) {
> +                     // if not visible, math etc is still auto, do not set 
> off
> +                     // clear both on and off bit
> +                     flags &= ~ToolbarBackend::ON;
> +                     flags &= ~ToolbarBackend::OFF;
> +             } else {
> +                     // for others, set the toolbar off
> +                     flags &= ~ToolbarBackend::ON;
> +                     flags |= ToolbarBackend::OFF;
> +             }
> +     }
> +     /*
> +     std::cout << "FLAGS: " << flags
> +             << " ON " << (flags & ToolbarBackend::ON) 
> +             << " OFF " << (flags & ToolbarBackend::OFF)
> +             << " L " << (flags & ToolbarBackend::LEFT) 
> +             << " R " << (flags & ToolbarBackend::RIGHT) 
> +             << " T " << (flags & ToolbarBackend::TOP) 
> +             << " B " << (flags & ToolbarBackend::BOTTOM) 
> +             << " MA " << (flags & ToolbarBackend::MATH) 
> +             << " RE " << (flags & ToolbarBackend::REVIEW) 
> +             << " TB " << (flags & ToolbarBackend::TABLE) 
> +             << std::endl;
> +     */
> +     // now set the flags
> +     tbb.flags = static_cast<lyx::ToolbarBackend::Flags>(flags);
> +}
> +
> +
>  void Toolbars::init()
>  {
>       // extracts the toolbars from the backend
>       ToolbarBackend::Toolbars::const_iterator cit = toolbarbackend.begin();
>       ToolbarBackend::Toolbars::const_iterator end = toolbarbackend.end();
>  
> -     for (; cit != end; ++cit)
> +     for (; cit != end; ++cit) {
> +             initFlags(const_cast<ToolbarBackend::Toolbar &>(*cit));
>               add(*cit);
> +     }
>  }
>  
>  
> @@ -84,6 +147,19 @@
>  }
>  
>  
> +void Toolbars::saveToolbarInfo()
> +{
> +     ToolbarSection & tb = LyX::ref().session().toolbars();
> +
> +     for (ToolbarBackend::Toolbars::const_iterator cit = 
> toolbarbackend.begin();
> +             cit != toolbarbackend.end(); ++cit) {
> +             ToolbarsMap::iterator it = toolbars_.find(cit->name);
> +             BOOST_ASSERT(it != toolbars_.end());
> +             it->second->saveInfo(tb.load(cit->name));
> +     }
> +}
> +
> +
>  void Toolbars::setLayout(string const & layout)
>  {
>       if (layout_)
> Index: src/frontends/qt4/QLToolbar.C
> ===================================================================
> --- src/frontends/qt4/QLToolbar.C     (revision 15675)
> +++ src/frontends/qt4/QLToolbar.C     (working copy)
> @@ -214,6 +214,25 @@
>  }
>  
>  
> +void QLToolbar::saveInfo(ToolbarSection::ToolbarInfo & info)
> +{
> +     // update Toolbar info with current toolbar status
> +     info.visible = QLToolbar::isVisible();
> +     Qt::ToolBarArea loc = owner_.toolBarArea(this);
> +
> +     if (loc == Qt::TopToolBarArea)
> +             info.location = ToolbarSection::ToolbarInfo::top;
> +     else if (loc == Qt::BottomToolBarArea)
> +             info.location = ToolbarSection::ToolbarInfo::bottom;
> +     else if (loc == Qt::RightToolBarArea)
> +             info.location = ToolbarSection::ToolbarInfo::right;
> +     else if (loc == Qt::LeftToolBarArea)
> +             info.location = ToolbarSection::ToolbarInfo::left;
> +     else
> +             info.location = ToolbarSection::ToolbarInfo::notset;
> +}
> +
> +
>  void QLToolbar::update()
>  {
>       // This is a speed bottleneck because this is called on every keypress
> Index: src/frontends/qt4/QLToolbar.h
> ===================================================================
> --- src/frontends/qt4/QLToolbar.h     (revision 15675)
> +++ src/frontends/qt4/QLToolbar.h     (working copy)
> @@ -22,6 +22,9 @@
>  #include <QToolBar>
>  #include <vector>
>  
> +#include "lyx_main.h"
> +#include "session.h"
> +
>  class QComboBox;
>  
>  namespace lyx {
> @@ -67,6 +70,7 @@
>       void add(FuncRequest const & func, lyx::docstring const & tooltip);
>       void hide(bool);
>       void show(bool);
> +     void saveInfo(ToolbarSection::ToolbarInfo & info);
>       void update();
>       LayoutBox * layout() const { return layout_.get(); }
>  
> Index: src/frontends/qt4/GuiView.C
> ===================================================================
> --- src/frontends/qt4/GuiView.C       (revision 15675)
> +++ src/frontends/qt4/GuiView.C       (working copy)
> @@ -182,6 +182,7 @@
>               session.sessionInfo().save("WindowPosX", 
> convert<string>(geometry.x()));
>               session.sessionInfo().save("WindowPosY", 
> convert<string>(geometry.y()));
>       }
> +     getToolbars().saveToolbarInfo();
>  }
>                                                 
>  void GuiView::setGeometry(unsigned int width,
> Index: src/frontends/Toolbars.h
> ===================================================================
> --- src/frontends/Toolbars.h  (revision 15675)
> +++ src/frontends/Toolbars.h  (working copy)
> @@ -26,6 +26,8 @@
>  #include "ToolbarBackend.h"
>  #include <boost/shared_ptr.hpp>
>  #include <map>
> +#include "lyx_main.h"
> +#include "session.h"
>  
>  
>  namespace lyx {
> @@ -64,6 +66,10 @@
>        *  metrics should be updated.
>        */
>       virtual void show(bool update_metrics) = 0;
> +     /** update toolbar information
> +     * ToolbarInfo will then be saved by session
> +     */
> +     virtual void saveInfo(ToolbarSection::ToolbarInfo & info) = 0;
>  
>       /// Refresh the contents of the bar.
>       virtual void update() = 0;
> @@ -86,6 +92,9 @@
>       /// Update the state of the toolbars.
>       void update(bool in_math, bool in_table, bool review);
>  
> +     /// save toolbar information
> +     void saveToolbarInfo();
> +
>       /// Select the right layout in the combox.
>       void setLayout(std::string const & layout);
>  
> @@ -128,6 +137,9 @@
>  
>       /// The last textclass layout list in the layout choice selector
>       int last_textclass_;
> +
> +     // load flags with saved values
> +     void initFlags(ToolbarBackend::Toolbar & tbb);
>  };
>  
>  /// Set the layout in the kernel when an entry has been selected
> Index: src/session.h
> ===================================================================
> --- src/session.h     (revision 15675)
> +++ src/session.h     (working copy)
> @@ -238,6 +238,59 @@
>  };
>  
>  
> +class ToolbarSection : SessionSection
> +{
> +public:
> +     /// information about a toolbar, not all information can be
> +     /// saved/restored by all frontends, but this class provides
> +     /// a superset of things that can be managed by session.
> +     class ToolbarInfo
> +     {
> +     public:
> +             ///
> +             ToolbarInfo() :
> +                     visible(true), location(notset) { }
> +             ///
> +             ToolbarInfo(bool v, int loc) :
> +                     visible(v), location(static_cast<Location>(loc)) { }
> +
> +     public:
> +             /// on/off
> +             bool visible;
> +
> +             /// location: this can be intepreted differently.
> +             enum Location {
> +                     top,
> +                     bottom,
> +                     left,
> +                     right,
> +                     notset
> +             };
> +
> +             Location location;
> +
> +             /// potentially, icons
> +     };
> +
> +     /// info for each toolbar
> +     typedef std::map<std::string, ToolbarInfo> ToolbarMap;
> +
> +public:
> +     ///
> +     void read(std::istream & is);
> +
> +     ///
> +     void write(std::ostream & os) const;
> +
> +     /// return reference to toolbar info, create a new one if needed
> +     ToolbarInfo & load(std::string const & name);
> +
> +private:
> +     /// toolbar information
> +     ToolbarMap toolbars;
> +};
> +
> +
>  class SessionInfoSection : SessionSection
>  {
>  public:
> @@ -307,6 +360,12 @@
>       BookmarksSection const & bookmarks() const { return bookmarks_; }
>  
>       ///
> +     ToolbarSection & toolbars() { return toolbars_; }
> +
> +     ///
> +     ToolbarSection const & toolbars() const { return toolbars_; }
> +
> +     ///
>       SessionInfoSection & sessionInfo() { return session_info; }
>  
>       ///
> @@ -336,6 +395,9 @@
>       BookmarksSection bookmarks_;
>  
>       ///
> +     ToolbarSection toolbars_;
> +
> +     ///
>       SessionInfoSection session_info;
>  };
>  


-- 
Peter Kümmel

Reply via email to