summaryrefslogtreecommitdiffstats
path: root/kdm/kfrontend/kgreeter.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'kdm/kfrontend/kgreeter.cpp')
-rw-r--r--kdm/kfrontend/kgreeter.cpp214
1 files changed, 191 insertions, 23 deletions
diff --git a/kdm/kfrontend/kgreeter.cpp b/kdm/kfrontend/kgreeter.cpp
index ebd303525..74fc6b090 100644
--- a/kdm/kfrontend/kgreeter.cpp
+++ b/kdm/kfrontend/kgreeter.cpp
@@ -27,6 +27,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "kdmconfig.h"
#include "kdmclock.h"
#include "kdm_greet.h"
+#include "kdmadmindialog.h"
#include "themer/kdmthemer.h"
#include "themer/kdmitem.h"
#include "themer/kdmlabel.h"
@@ -38,6 +39,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include <klistview.h>
#include <ksimpleconfig.h>
#include <kstringhandler.h>
+#include <kdebug.h>
#undef Unsorted // x headers suck - make tqdir.h work with --enable-final
#include <tqdir.h>
@@ -46,6 +48,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include <tqmemarray.h>
#include <tqimage.h>
#include <tqmovie.h>
+#include <tqpainter.h>
#include <tqpopupmenu.h>
#include <tqtimer.h>
#include <tqheader.h>
@@ -57,6 +60,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include <tqaccel.h>
#include <tqstring.h>
#include <tqeventloop.h>
+#include <tqbitmap.h>
#include <pwd.h>
#include <grp.h>
@@ -64,27 +68,46 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include <unistd.h>
#include <fcntl.h>
#include <sys/types.h>
+#include <utmp.h>
+#include <utmpx.h>
#include <X11/Xlib.h>
class UserListView : public KListView {
public:
- UserListView( TQWidget *parent = 0, const char *name = 0 )
+ UserListView( bool _them, TQWidget *parent = 0, const char *name = 0 )
: KListView( parent, name )
- , cachedSizeHint( -1, 0 )
+ , themed(_them), cachedSizeHint( -1, 0 )
{
setSizePolicy( TQSizePolicy::Preferred, TQSizePolicy::Ignored );
header()->hide();
addColumn( TQString::null );
setColumnAlignment( 0, AlignVCenter );
setResizeMode( TQListView::LastColumn );
+ if (themed) {
+ setBackgroundMode( Qt::NoBackground );
+ viewport()->setBackgroundMode( Qt::NoBackground );
+ setFrameStyle( TQFrame::NoFrame );
+ }
}
+ bool themed;
mutable TQSize cachedSizeHint;
- protected:
+ int sumHeight() const
+ {
+ int sum = 0;
+ for (TQListViewItem *itm = firstChild(); itm; itm = itm->nextSibling()) {
+ sum += itm->height();
+ }
+ return sum;
+ }
+public:
virtual TQSize sizeHint() const
{
+ if (themed)
+ return KListView::sizeHint();
+
if (!cachedSizeHint.isValid()) {
constPolish();
uint maxw = 0;
@@ -99,9 +122,24 @@ class UserListView : public KListView {
}
return cachedSizeHint;
}
+ virtual void paintEmptyArea ( TQPainter * p, const TQRect & rect )
+ {
+ if (!themed)
+ return KListView::paintEmptyArea(p, rect );
+
+ const TQPixmap *pm = paletteBackgroundPixmap();
+ if (!pm || pm->isNull())
+ return;
+
+ kdDebug() << "paintEmpty " << rect << endl;
+ TQRect devRect = p->xForm( rect );
+ kdDebug() << "paintEmpty2 " << devRect << endl;
+ p->drawPixmap(0, 0, *pm, devRect.left(), devRect.top() );
+ }
+
+ TQPixmap background;
};
-
int KGreeter::curPlugin = -1;
PluginList KGreeter::pluginList;
@@ -116,12 +154,14 @@ KGreeter::KGreeter( bool framed )
, curSel( -1 )
, prevValid( true )
, needLoad( false )
+ , themed( framed )
{
stsFile = new KSimpleConfig( _stsFile );
stsFile->setGroup( "PrevUser" );
if (_userList) {
- userView = new UserListView( this );
+ readFacesList();
+ userView = new UserListView( framed, this );
connect( userView, TQT_SIGNAL(clicked( TQListViewItem * )),
TQT_SLOT(slotUserClicked( TQListViewItem * )) );
connect( userView, TQT_SIGNAL(doubleClicked( TQListViewItem * )),
@@ -129,10 +169,8 @@ KGreeter::KGreeter( bool framed )
}
if (_userCompletion)
userList = new TQStringList;
- if (userView || userList)
- insertUsers();
- sessMenu = new TQPopupMenu( this );
+ sessMenu = new TQPopupMenu( this );
connect( sessMenu, TQT_SIGNAL(activated( int )),
TQT_SLOT(slotSessionSelected( int )) );
insertSessions();
@@ -151,6 +189,33 @@ KGreeter::~KGreeter()
delete stsFile;
}
+void KGreeter::readFacesList()
+{
+ FILE *f = fopen( TQFile::encodeName( _faceDir + "/.randomlist" ), "rt" );
+ if ( !f )
+ return;
+ TQTextIStream is( f );
+ while ( !is.eof() )
+ {
+ TQString line = is.readLine().simplifyWhiteSpace();
+ if ( line.isEmpty() )
+ continue;
+ TQString icon;
+ int index = line.find( ' ' );
+ if ( index > 0 ) {
+ icon = line.left( index );
+ line = line.mid( index );
+ } else {
+ icon = line;
+ line = TQString::null;
+ }
+ randomFaces.push_back( icon );
+ TQStringList list = TQStringList::split( ' ', line );
+ for ( TQStringList::ConstIterator it = list.begin(); it != list.end(); ++it )
+ randomFacesMap[*it] = icon;
+ }
+}
+
class UserListViewItem : public KListViewItem {
public:
UserListViewItem( UserListView *parent, const TQString &text,
@@ -164,6 +229,14 @@ class UserListViewItem : public KListViewItem {
parent->cachedSizeHint.setWidth( -1 );
}
+ virtual void paintCell(TQPainter *p, const TQColorGroup &cg, int column, int width, int alignment)
+ {
+ if (((UserListView*)listView())->themed)
+ TQListViewItem::paintCell(p, cg, column, width, alignment);
+ else
+ KListViewItem::paintCell(p, cg, column, width, alignment);
+ }
+
TQString login;
};
@@ -232,10 +305,23 @@ KGreeter::insertUser( const TQImage &default_pix,
TQSize ns( 48, 48 );
if (p.size() != ns)
p = p.convertDepth( 32 ).smoothScale( ns, TQImage::ScaleMin );
- goto gotit;
+ break;
} while (--nd >= 0);
- p = default_pix;
- gotit:
+
+ if ( p.isNull() && randomFaces.count() ) {
+ TQString randomFace = randomFacesMap[username];
+ if ( randomFace.isNull() ) {
+ TQStringList::size_type index = 0;
+ for ( size_t i = 0; i < username.length(); ++i )
+ index += ( 0x7f - username.at( i ).latin1() ) % 37;
+ randomFace = randomFaces[ index % randomFaces.count() ];
+ }
+ p.load( _faceDir + "/../pics/users/" + randomFace + ".png" );
+ }
+
+ if ( p.isNull() )
+ p = default_pix;
+
TQString realname = KStringHandler::from8Bit( ps->pw_gecos );
realname.truncate( realname.find( ',' ) );
if (realname.isEmpty() || realname == username)
@@ -289,7 +375,7 @@ UserList::UserList( char **in )
}
void
-KGreeter::insertUsers()
+KGreeter::insertUsers(int limit_users)
{
struct passwd *ps;
@@ -309,6 +395,8 @@ KGreeter::insertUsers()
if (_showUsers == SHOW_ALL) {
UserList noUsers( _noUsers );
TQDict<int> dupes( 1000 );
+ TQStringList toinsert;
+ int count = 0;
for (setpwent(); (ps = getpwent()) != 0;) {
if (*ps->pw_dir && *ps->pw_shell &&
(ps->pw_uid >= (unsigned)_lowUserId ||
@@ -320,10 +408,53 @@ KGreeter::insertUsers()
TQString username( TQFile::decodeName( ps->pw_name ) );
if (!dupes.find( username )) {
dupes.insert( username, (int *)-1 );
- insertUser( default_pix, username, ps );
+ toinsert.append( username );
+
+ if ( limit_users >= 0 && ++count > limit_users )
+ break;
}
}
}
+ if ( limit_users >= 0 && ++count > limit_users ) {
+ utmpname( _PATH_WTMP );
+ setutxent();
+ toinsert = TQStringList();
+ dupes.clear();
+
+ for ( count = 0; count < limit_users; ) {
+ struct utmpx * ent = getutxent();
+ if ( !ent )
+ break;
+ struct passwd *ps = getpwnam( ent->ut_user );
+ if (ps && *ps->pw_dir && *ps->pw_shell &&
+ (ps->pw_uid >= (unsigned)_lowUserId ||
+ !ps->pw_uid && _showRoot) &&
+ ps->pw_uid <= (unsigned)_highUserId &&
+ !noUsers.hasUser( ps->pw_name ) &&
+ !noUsers.hasGroup( ps->pw_gid ))
+ {
+ TQString username( TQFile::decodeName( ent->ut_user ) );
+ if (!dupes.find( username )) {
+ dupes.insert( username, (int *)-1 );
+ toinsert.append( username );
+ count++;
+ }
+ }
+
+
+ }
+ endutxent();
+ }
+
+ for ( TQStringList::ConstIterator it = toinsert.begin();
+ it != toinsert.end(); ++it )
+ {
+ // pretty stupid to do another lookup round, but the number is limited
+ // and caching struct passwd is pretty ugly
+ struct passwd *ps = getpwnam( TQFile::encodeName( *it ) );
+ if ( ps )
+ insertUser( default_pix, *it, ps );
+ }
} else {
UserList users( _users );
if (users.hasGroups()) {
@@ -379,7 +510,7 @@ KGreeter::insertSessions()
for (char **dit = _sessionsDirs; *dit; ++dit) {
TQStringList ents = TQDir( *dit ).entryList();
for (TQStringList::ConstIterator it = ents.begin(); it != ents.end(); ++it)
- if ((*it).endsWith( ".desktop" )) {
+ if ((*it).endsWith( ".desktop" ) && !(*it).endsWith("admin.desktop")) {
KSimpleConfig dsk( TQString( *dit ).append( '/' ).append( *it ) );
dsk.setGroup( "Desktop Entry" );
putSession( (*it).left( (*it).length() - 8 ),
@@ -517,6 +648,17 @@ KGreeter::slotLoadPrevWM()
return;
}
} else {
+ if (!strcmp(sess, "admin")) {
+ // need to get the original
+ GSendInt( G_GetDmrc);
+ GSendStr( "OrigSession");
+ sess = GRecvStr();
+ if (!sess) {
+ free(sess);
+ sess = strdup("default");
+ }
+ }
+
for (uint i = 0; i < sessionTypes.count() && !sessionTypes[i].hid; i++)
if (sessionTypes[i].type == sess) {
free( sess );
@@ -718,21 +860,24 @@ KStdGreeter::KStdGreeter()
hbox2->addStretch( 1 );
if (sessMenu->count() > 1) {
- inserten( i18n("Session &Type"), ALT+Key_T, sessMenu );
+ inserten( i18n("Session &Type"), 0, sessMenu );
needSep = true;
}
if (plugMenu) {
- inserten( i18n("&Authentication Method"), ALT+Key_A, plugMenu );
+ inserten( i18n("&Authentication Method"), 0, plugMenu );
needSep = true;
}
#ifdef XDMCP
- completeMenu( LOGIN_LOCAL_ONLY, ex_choose, i18n("&Remote Login"), ALT+Key_R );
+ completeMenu( LOGIN_LOCAL_ONLY, ex_choose, i18n("&Remote Login"), 0 );
#else
completeMenu();
#endif
+ if (userView || userList)
+ insertUsers();
+
if (optMenu)
menuButton->setPopup( optMenu );
else
@@ -826,6 +971,9 @@ KThemedGreeter::KThemedGreeter()
if (xauth_warning && (_authorized || !_authComplain))
xauth_warning->hide( true );
+ if (userView || userList)
+ insertUsers( 7 ); // TODO: find out how many are a good value
+
// if (!_greetString.isEmpty()) {
// }
// clock = new KdmClock( this, "clock" );
@@ -851,12 +999,8 @@ KThemedGreeter::KThemedGreeter()
if ((itm = themer->findNode( "session_button" ))) {
if (sessMenu->count() <= 1)
itm->hide( true );
- else {
+ else
session_button = itm;
- TQAccel *accel = new TQAccel( this );
- accel->insertItem( ALT+Key_T, 0 );
- connect( accel, TQT_SIGNAL(activated( int )), TQT_SLOT(slotSessMenu()) );
- }
} else {
if (sessMenu->count() > 1) {
inserten( i18n("Session &Type"), ALT+Key_T, sessMenu );
@@ -864,6 +1008,12 @@ KThemedGreeter::KThemedGreeter()
}
}
+ admin_button = themer->findNode( "admin_button");
+ if ( admin_button ) {
+ if ( !_useAdminSession )
+ admin_button->hide( true );
+ }
+
if (plugMenu) {
inserten( i18n("&Authentication Method"), ALT+Key_A, plugMenu );
needSep = true;
@@ -899,8 +1049,8 @@ KThemedGreeter::pluginSetup()
inherited::pluginSetup();
if (userView && verify->entitiesLocal() && verify->entityPresettable() && userlist_rect) {
+ userView->setMaximumHeight( userView->sumHeight() );
userlist_rect->setWidget( userView );
- userView->show();
} else {
if (userView)
userView->hide();
@@ -916,12 +1066,17 @@ KThemedGreeter::verifyFailed()
{
// goButton->setEnabled( false );
inherited::verifyFailed();
+ if (userView)
+ userView->setEnabled(false);
}
void
KThemedGreeter::verifyRetry()
{
// goButton->setEnabled( true );
+ if (userView)
+ userView->setEnabled(true);
+
}
TQString KThemedGreeter::timedUser = TQString::null;
@@ -966,6 +1121,8 @@ KThemedGreeter::slotThemeActivated( const TQString &id )
slotSessMenu();
else if (id == "system_button")
slotActionMenu();
+ else if (id == "admin_button")
+ slotAskAdminPassword();
}
void
@@ -992,4 +1149,15 @@ KThemedGreeter::keyPressEvent( TQKeyEvent *e )
accept();
}
+void
+KThemedGreeter::slotAskAdminPassword()
+{
+ KDMAdmin k(curUser, this);
+ if (k.exec()) {
+ GSendInt(G_Ready);
+ hide();
+ done(ex_exit);
+ }
+}
+
#include "kgreeter.moc"