Change focused signal to use the new signal system

This commit is contained in:
Henrik Kinnunen 2008-09-28 10:46:49 +02:00
parent ed53f3c623
commit bcf37890b6
11 changed files with 84 additions and 41 deletions

View file

@ -1,5 +1,9 @@
(Format: Year/Month/Day)
Changes for 1.1.2
*08/09/28:
* Change focused window signal to use the new signal system (Henrik)
FbTk/Signal.hh, FocusControl.cc, FocusableList.hh/cc, Screen.hh/cc
Window.hh/cc, fluxbox.hh/cc
*08/09/21:
* Changed icon list signal in BScreen to use the new signal system
(Henrik)

View file

@ -191,8 +191,8 @@ public:
class SignalTracker {
public:
/// Internal type, do not use.
typedef std::list< std::pair<SigImpl::SignalHolder*,
SigImpl::SignalHolder::SlotID> > Connections;
typedef std::map<SigImpl::SignalHolder*,
SigImpl::SignalHolder::SlotID> Connections;
typedef Connections::iterator TrackID; ///< \c ID type for join/leave.
~SignalTracker() {
@ -203,9 +203,13 @@ public:
/// @return A tracking ID ( not unique )
template <typename Signal, typename Functor>
TrackID join(Signal& sig, const Functor& functor) {
return
m_connections.insert(m_connections.end(),
Connections::value_type(&sig, sig.connect(functor)));
ValueType value = std::make_pair(&sig, sig.connect(functor));
std::pair<TrackID, bool> ret = m_connections.insert(value);
if ( !ret.second ) {
// failed to insert this functor
sig.disconnect(value.second);
}
return ret.first;
}
/// Leave tracking for a signal
@ -217,23 +221,29 @@ public:
/// Leave tracking for a signal
/// @param sig the signal to leave
template <typename Signal>
void leave(const Signal &sig) {
m_connections.erase(&sig);
void leave(Signal &sig) {
Iterator it = m_connections.find(&sig);
if (it != m_connections.end()) {
it->first->disconnect( it->second );
m_connections.erase(it);
}
}
void leaveAll() {
// disconnect all connections
for ( Connections::iterator conIt = m_connections.begin();
conIt != m_connections.end(); ) {
for ( Iterator conIt = m_connections.begin();
conIt != m_connections.end(); ++conIt) {
// keep temporary, while disconnecting we can
// in some strange cases get a call to this again
Connections::value_type tmp = *conIt;
conIt = m_connections.erase(conIt);
ValueType tmp = *conIt;
m_connections.erase(conIt);
tmp.first->disconnect(tmp.second);
}
}
private:
typedef Connections::value_type ValueType;
typedef Connections::iterator Iterator;
/// holds all connections to different signals and slots.
Connections m_connections;
};

View file

@ -560,9 +560,9 @@ void FocusControl::setFocusedWindow(WinClient *client) {
// update AtomHandlers and/or other stuff...
if (screen)
screen->focusedWindowSig().notify();
screen->focusedWindowSig().emit(*screen, s_focused_fbwindow, s_focused_window);
if (old_screen && screen != old_screen)
old_screen->focusedWindowSig().notify();
old_screen->focusedWindowSig().emit(*old_screen, s_focused_fbwindow, s_focused_window);
}
////////////////////// FocusControl RESOURCES

View file

@ -100,8 +100,10 @@ void FocusableList::init() {
join(m_screen.currentWorkspaceSig(),
FbTk::MemFun(*this, &FocusableList::workspaceChanged));
}
if (m_pat->dependsOnFocusedWindow())
m_screen.focusedWindowSig().attach(this);
if (m_pat->dependsOnFocusedWindow()) {
join(m_screen.focusedWindowSig(),
FbTk::MemFun(*this, &FocusableList::focusedWindowChanged));
}
}
void FocusableList::update(FbTk::Subject *subj) {
@ -150,8 +152,7 @@ void FocusableList::update(FbTk::Subject *subj) {
if (insertFromParent(*win))
m_ordersig.notify(win);
}
} else if (subj == &m_screen.focusedWindowSig())
reset();
}
}
void FocusableList::checkUpdate(Focusable &win) {
@ -315,3 +316,9 @@ void FocusableList::attachChild(FocusableList &child) const {
void FocusableList::workspaceChanged(BScreen &screen) {
reset();
}
void FocusableList::focusedWindowChanged(BScreen &screen,
FluxboxWindow *focused_win,
WinClient *client) {
reset();
}

View file

@ -35,6 +35,8 @@
class BScreen;
class Focusable;
class WinClient;
class FluxboxWindow;
class FocusableList: public FbTk::Observer, private FbTk::NotCopyable,
private FbTk::SignalTracker {
@ -112,8 +114,8 @@ private:
void detachSignals(Focusable &win);
void reset();
void attachChild(FocusableList &child) const;
void workspaceChanged(BScreen& screen);
void workspaceChanged(BScreen &screen);
void focusedWindowChanged(BScreen &screen, FluxboxWindow *win, WinClient *client);
std::auto_ptr<ClientPattern> m_pat;
const FocusableList *m_parent;
BScreen &m_screen;

View file

@ -340,7 +340,6 @@ BScreen::BScreen(FbTk::ResourceManager &rm,
const string &altscreenname,
int scrn, int num_layers) :
m_workspace_area_sig(*this), // workspace area signal
m_focusedwindow_sig(*this), // focused window signal
m_reconfigure_sig(*this), // reconfigure signal
m_resize_sig(*this),
m_layermanager(num_layers),

View file

@ -223,7 +223,7 @@ public:
/// current workspace signal
ScreenSignal &currentWorkspaceSig() { return m_currentworkspace_sig; }
/// focused window signal
FbTk::Subject &focusedWindowSig() { return m_focusedwindow_sig; }
FbTk::Signal<void, BScreen&, FluxboxWindow*, WinClient*> &focusedWindowSig() { return m_focusedwindow_sig; }
/// reconfigure signal
FbTk::Subject &reconfigureSig() { return m_reconfigure_sig; }
FbTk::Subject &resizeSig() { return m_resize_sig; }
@ -494,10 +494,10 @@ private:
ScreenSubject
m_workspace_area_sig, ///< workspace area changed signal
m_focusedwindow_sig, ///< focused window signal
m_reconfigure_sig, ///< reconfigure signal
m_resize_sig; ///< resize signal
FbTk::Signal<void, BScreen&, FluxboxWindow*, WinClient*> m_focusedwindow_sig; ///< focused window signal
ScreenSignal m_iconlist_sig; ///< notify if a window gets iconified/deiconified
ScreenSignal m_clientlist_sig; ///< client signal
ScreenSignal m_bg_change_sig; ///< background change signal

View file

@ -49,6 +49,7 @@
#include "FbTk/KeyUtil.hh"
#include "FbTk/SimpleCommand.hh"
#include "FbTk/Select2nd.hh"
#include "FbTk/MemFun.hh"
#ifdef HAVE_CONFIG_H
#include "config.h"
@ -1450,8 +1451,10 @@ void FluxboxWindow::setFullscreen(bool flag) {
frame().applyState();
setFullscreenLayer(); // calls stateSig().notify()
if (!isFocused())
screen().focusedWindowSig().attach(this);
if (!isFocused()) {
join(screen().focusedWindowSig(),
FbTk::MemFun(*this, &FluxboxWindow::focusedWindowChanged));
}
} else if (!flag && isFullscreen()) {
@ -1769,12 +1772,14 @@ void FluxboxWindow::setFocusFlag(bool focus) {
// if we're fullscreen and another window gains focus on the same head,
// then we need to let the user see it
if (m_state.fullscreen && !focus)
screen().focusedWindowSig().attach(this);
if (m_state.fullscreen && !focus) {
join(screen().focusedWindowSig(),
FbTk::MemFun(*this, &FluxboxWindow::focusedWindowChanged));
}
if (m_state.fullscreen && focus) {
moveToLayer(::Layer::ABOVE_DOCK);
screen().focusedWindowSig().detach(this);
leave(screen().focusedWindowSig());
}
if (focus != frame().focused())
@ -2721,9 +2726,6 @@ void FluxboxWindow::update(FbTk::Subject *subj) {
titleSig().notify();
}
} else if (subj == &screen().focusedWindowSig()) {
if (FocusControl::focusedFbWindow())
setFullscreenLayer();
} else if (subj == &m_theme.reconfigSig()) {
frame().applyDecorations();
sendConfigureNotify();
@ -3867,3 +3869,10 @@ void FluxboxWindow::setWindowType(WindowState::WindowType type) {
* _NET_WM_WINDOW_TYPE_UTILITY
*/
}
void FluxboxWindow::focusedWindowChanged(BScreen &screen,
FluxboxWindow *focused_win, WinClient* client) {
if (focused_win) {
setFullscreenLayer();
}
}

View file

@ -31,12 +31,14 @@
#include "FbTk/Observer.hh"
#include "FbTk/EventHandler.hh"
#include "FbTk/XLayerItem.hh"
#include "FbTk/Signal.hh"
#include "FbWinFrame.hh"
#include "Focusable.hh"
#include "FocusableTheme.hh"
#include "WinButton.hh"
#include <sys/time.h>
#include <vector>
#include <string>
@ -58,7 +60,8 @@ class XLayer;
/// Creates the window frame and handles any window event for it
class FluxboxWindow: public Focusable, public FbTk::Observer,
public FbTk::EventHandler {
public FbTk::EventHandler,
private FbTk::SignalTracker {
public:
/// Motif wm Hints
enum {
@ -521,6 +524,8 @@ private:
static void ungrabPointer(Time time);
void associateClient(WinClient &client);
/// Called when focused changed, and is attached when it is not in fullscreen mode
void focusedWindowChanged(BScreen &screen, FluxboxWindow *focused_win, WinClient* client);
// state and hint signals
WinSubject m_hintsig,

View file

@ -453,9 +453,11 @@ void Fluxbox::initScreen(BScreen *screen) {
screen->initWindows();
// attach screen signals to this
screen->focusedWindowSig().attach(this);
screen->workspaceAreaSig().attach(this);
join(screen->focusedWindowSig(),
FbTk::MemFun(*this, &Fluxbox::focusedWindowChanged));
join(screen->clientListSig(),
FbTk::MemFun(*this, &Fluxbox::clientListChanged));
@ -1105,15 +1107,7 @@ void Fluxbox::update(FbTk::Subject *changedsub) {
} else if (typeid(*changedsub) == typeid(BScreen::ScreenSubject)) {
BScreen::ScreenSubject *subj = dynamic_cast<BScreen::ScreenSubject *>(changedsub);
BScreen &screen = subj->screen();
if ((&(screen.focusedWindowSig())) == changedsub) {
for (AtomHandlerContainerIt it= m_atomhandler.begin();
it != m_atomhandler.end(); it++) {
(*it).first->updateFocusedWindow(screen,
(FocusControl::focusedWindow() ?
FocusControl::focusedWindow()->window() :
0));
}
} else if ((&(screen.workspaceAreaSig())) == changedsub) {
if ((&(screen.workspaceAreaSig())) == changedsub) {
for (AtomHandlerContainerIt it= m_atomhandler.begin();
it != m_atomhandler.end(); ++it) {
if ((*it).first->update())
@ -1537,3 +1531,12 @@ void Fluxbox::clientListChanged(BScreen &screen) {
(*it).first->updateClientList(screen);
}
}
void Fluxbox::focusedWindowChanged(BScreen &screen,
FluxboxWindow* win,
WinClient* client) {
for (AtomHandlerContainerIt it= m_atomhandler.begin();
it != m_atomhandler.end(); it++) {
(*it).first->updateFocusedWindow(screen, client ? client->window() : 0 );
}
}

View file

@ -209,6 +209,10 @@ private:
void workspaceNamesChanged(BScreen &screen);
/// Called when the client list changed.
void clientListChanged(BScreen &screen);
/// Called when the focused window changed on a screen
void focusedWindowChanged(BScreen &screen,
FluxboxWindow* win,
WinClient* client);
std::auto_ptr<FbAtoms> m_fbatoms;