mirror of
https://github.com/xiaoyifang/goldendict-ng.git
synced 2024-11-27 19:24:08 +00:00
opt: rewrite solo mode in the dictionary bar (#1073)
* action: output new syntax * opt: dictionary bar modification,Ctrl for solo selection, Shift restore * opt: only the first Ctrl + Click event store the existed dictionaries * [autofix.ci] apply automated fixes * opt: ctrl switch between single and all dictionaries * doc: add shortcut document about solo mode --------- Co-authored-by: YiFang Xiao <yifang.xiao@noreply.com> Co-authored-by: autofix-ci[bot] <114827586+autofix-ci[bot]@users.noreply.github.com>
This commit is contained in:
parent
8cd29d527a
commit
3359f6636a
|
@ -13,7 +13,7 @@ DictionaryBar::DictionaryBar( QWidget * parent,
|
||||||
QString const & _editDictionaryCommand,
|
QString const & _editDictionaryCommand,
|
||||||
unsigned short const & maxDictionaryRefsInContextMenu_ ):
|
unsigned short const & maxDictionaryRefsInContextMenu_ ):
|
||||||
QToolBar( tr( "&Dictionary Bar" ), parent ),
|
QToolBar( tr( "&Dictionary Bar" ), parent ),
|
||||||
mutedDictionaries( 0 ),
|
mutedDictionaries( nullptr ),
|
||||||
configEvents( events ),
|
configEvents( events ),
|
||||||
editDictionaryCommand( _editDictionaryCommand ),
|
editDictionaryCommand( _editDictionaryCommand ),
|
||||||
maxDictionaryRefsInContextMenu( maxDictionaryRefsInContextMenu_ )
|
maxDictionaryRefsInContextMenu( maxDictionaryRefsInContextMenu_ )
|
||||||
|
@ -52,16 +52,16 @@ void DictionaryBar::setDictionaries( vector< sptr< Dictionary::Class > > const &
|
||||||
clear();
|
clear();
|
||||||
dictActions.clear();
|
dictActions.clear();
|
||||||
|
|
||||||
for ( unsigned x = 0; x < dictionaries.size(); ++x ) {
|
for ( const auto & dictionary : dictionaries ) {
|
||||||
QIcon icon = dictionaries[ x ]->getIcon();
|
QIcon icon = dictionary->getIcon();
|
||||||
|
|
||||||
QString dictName = QString::fromUtf8( dictionaries[ x ]->getName().c_str() );
|
QString dictName = QString::fromUtf8( dictionary->getName().c_str() );
|
||||||
|
|
||||||
QAction * action = addAction( icon, elideDictName( dictName ) );
|
QAction * action = addAction( icon, elideDictName( dictName ) );
|
||||||
|
|
||||||
action->setToolTip( dictName ); // Tooltip need not be shortened
|
action->setToolTip( dictName ); // Tooltip need not be shortened
|
||||||
|
|
||||||
QString id = QString::fromStdString( dictionaries[ x ]->getId() );
|
QString id = QString::fromStdString( dictionary->getId() );
|
||||||
|
|
||||||
action->setData( id );
|
action->setData( id );
|
||||||
|
|
||||||
|
@ -91,21 +91,21 @@ void DictionaryBar::showContextMenu( QContextMenuEvent * event, bool extended )
|
||||||
{
|
{
|
||||||
QMenu menu( this );
|
QMenu menu( this );
|
||||||
|
|
||||||
QAction * editAction = menu.addAction( QIcon( ":/icons/bookcase.svg" ), tr( "Edit this group" ) );
|
const QAction * editAction = menu.addAction( QIcon( ":/icons/bookcase.svg" ), tr( "Edit this group" ) );
|
||||||
|
|
||||||
QAction * infoAction = NULL;
|
const QAction * infoAction = nullptr;
|
||||||
QAction * headwordsAction = NULL;
|
const QAction * headwordsAction = nullptr;
|
||||||
QAction * editDictAction = NULL;
|
const QAction * editDictAction = nullptr;
|
||||||
QAction * openDictFolderAction = NULL;
|
const QAction * openDictFolderAction = nullptr;
|
||||||
QString dictFilename;
|
QString dictFilename;
|
||||||
|
|
||||||
QAction * dictAction = actionAt( event->x(), event->y() );
|
const QAction * dictAction = actionAt( event->x(), event->y() );
|
||||||
if ( dictAction ) {
|
if ( dictAction ) {
|
||||||
Dictionary::Class * pDict = NULL;
|
Dictionary::Class * pDict = nullptr;
|
||||||
QString id = dictAction->data().toString();
|
QString const id = dictAction->data().toString();
|
||||||
for ( unsigned i = 0; i < allDictionaries.size(); i++ ) {
|
for ( const auto & dictionary : allDictionaries ) {
|
||||||
if ( id.compare( allDictionaries[ i ]->getId().c_str() ) == 0 ) {
|
if ( id.compare( dictionary->getId().c_str() ) == 0 ) {
|
||||||
pDict = allDictionaries[ i ].get();
|
pDict = dictionary.get();
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -134,7 +134,7 @@ void DictionaryBar::showContextMenu( QContextMenuEvent * event, bool extended )
|
||||||
|
|
||||||
unsigned refsAdded = 0;
|
unsigned refsAdded = 0;
|
||||||
|
|
||||||
for ( QList< QAction * >::iterator i = dictActions.begin(); i != dictActions.end(); ++i ) {
|
for ( const auto & dictAction : dictActions ) {
|
||||||
|
|
||||||
// Enough! Or the menu would become too large.
|
// Enough! Or the menu would become too large.
|
||||||
if ( refsAdded++ >= maxDictionaryRefsInContextMenu && !extended ) {
|
if ( refsAdded++ >= maxDictionaryRefsInContextMenu && !extended ) {
|
||||||
|
@ -144,11 +144,11 @@ void DictionaryBar::showContextMenu( QContextMenuEvent * event, bool extended )
|
||||||
}
|
}
|
||||||
|
|
||||||
// We need new action, since the one we have has text elided
|
// We need new action, since the one we have has text elided
|
||||||
QAction * action = menu.addAction( ( *i )->icon(), ( *i )->toolTip() );
|
QAction * action = menu.addAction( dictAction->icon(), dictAction->toolTip() );
|
||||||
|
|
||||||
action->setCheckable( true );
|
action->setCheckable( true );
|
||||||
action->setChecked( ( *i )->isChecked() );
|
action->setChecked( dictAction->isChecked() );
|
||||||
action->setData( QVariant::fromValue( (void *)*i ) );
|
action->setData( QVariant::fromValue( (void *)dictAction ) );
|
||||||
// Force "icon in menu" on all platforms, for
|
// Force "icon in menu" on all platforms, for
|
||||||
// usability reasons.
|
// usability reasons.
|
||||||
action->setIconVisibleInMenu( true );
|
action->setIconVisibleInMenu( true );
|
||||||
|
@ -156,17 +156,16 @@ void DictionaryBar::showContextMenu( QContextMenuEvent * event, bool extended )
|
||||||
|
|
||||||
connect( this, &DictionaryBar::closePopupMenu, &menu, &QWidget::close );
|
connect( this, &DictionaryBar::closePopupMenu, &menu, &QWidget::close );
|
||||||
|
|
||||||
QAction * result = menu.exec( event->globalPos() );
|
const QAction * result = menu.exec( event->globalPos() );
|
||||||
|
|
||||||
if ( result && result == infoAction ) {
|
if ( result && result == infoAction ) {
|
||||||
QString id = dictAction->data().toString();
|
QString const id = dictAction->data().toString();
|
||||||
emit showDictionaryInfo( id );
|
emit showDictionaryInfo( id );
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( result && result == headwordsAction ) {
|
if ( result && result == headwordsAction ) {
|
||||||
std::string id = dictAction->data().toString().toStdString();
|
std::string const id = dictAction->data().toString().toStdString();
|
||||||
// TODO: use `Dictionary::class*` instead of `QString id` at action->setData to remove all similar `for` loops
|
|
||||||
for ( const auto & dict : allDictionaries ) {
|
for ( const auto & dict : allDictionaries ) {
|
||||||
if ( id == dict->getId() ) {
|
if ( id == dict->getId() ) {
|
||||||
emit showDictionaryHeadwords( dict.get() );
|
emit showDictionaryHeadwords( dict.get() );
|
||||||
|
@ -177,14 +176,14 @@ void DictionaryBar::showContextMenu( QContextMenuEvent * event, bool extended )
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( result && result == openDictFolderAction ) {
|
if ( result && result == openDictFolderAction ) {
|
||||||
QString id = dictAction->data().toString();
|
QString const id = dictAction->data().toString();
|
||||||
emit openDictionaryFolder( id );
|
emit openDictionaryFolder( id );
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( result && result == editDictAction ) {
|
if ( result && result == editDictAction ) {
|
||||||
QString command( editDictionaryCommand );
|
QString command( editDictionaryCommand );
|
||||||
command.replace( "%GDDICT%", "\"" + dictFilename + "\"" );
|
command.replace( "%GDDICT%", QString( R"("%1")" ).arg( dictFilename ) );
|
||||||
if ( !QProcess::startDetached( command, QStringList() ) )
|
if ( !QProcess::startDetached( command, QStringList() ) )
|
||||||
QApplication::beep();
|
QApplication::beep();
|
||||||
}
|
}
|
||||||
|
@ -212,11 +211,11 @@ void DictionaryBar::mutedDictionariesChanged()
|
||||||
|
|
||||||
setUpdatesEnabled( false );
|
setUpdatesEnabled( false );
|
||||||
|
|
||||||
for ( QList< QAction * >::iterator i = dictActions.begin(); i != dictActions.end(); ++i ) {
|
for ( const auto & dictAction : dictActions ) {
|
||||||
bool isUnmuted = !mutedDictionaries->contains( ( *i )->data().toString() );
|
bool const isUnmuted = !mutedDictionaries->contains( dictAction->data().toString() );
|
||||||
|
|
||||||
if ( isUnmuted != ( *i )->isChecked() )
|
if ( isUnmuted != dictAction->isChecked() )
|
||||||
( *i )->setChecked( isUnmuted );
|
dictAction->setChecked( isUnmuted );
|
||||||
}
|
}
|
||||||
|
|
||||||
setUpdatesEnabled( true );
|
setUpdatesEnabled( true );
|
||||||
|
@ -227,15 +226,14 @@ void DictionaryBar::actionWasTriggered( QAction * action )
|
||||||
if ( !mutedDictionaries )
|
if ( !mutedDictionaries )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
QString id = action->data().toString();
|
QString const id = action->data().toString();
|
||||||
|
|
||||||
if ( id.isEmpty() )
|
if ( id.isEmpty() )
|
||||||
return; // Some weird action, not our button
|
return; // Some weird action, not our button
|
||||||
|
|
||||||
if ( QApplication::keyboardModifiers() & ( Qt::ControlModifier | Qt::ShiftModifier ) ) {
|
if ( QApplication::keyboardModifiers() & ( Qt::ControlModifier | Qt::ShiftModifier ) ) {
|
||||||
// Solo mode -- either use the dictionary exclusively, or toggle
|
// Ctrl ,solo mode with single dictionary
|
||||||
// back all dictionaries if we do that already.
|
// Shift,toggle back the previous dictionaries
|
||||||
|
|
||||||
// Are we solo already?
|
// Are we solo already?
|
||||||
|
|
||||||
bool isSolo = true;
|
bool isSolo = true;
|
||||||
|
@ -243,30 +241,35 @@ void DictionaryBar::actionWasTriggered( QAction * action )
|
||||||
// For solo, all dictionaries must be unchecked, since we're handling
|
// For solo, all dictionaries must be unchecked, since we're handling
|
||||||
// the result of the dictionary being (un)checked, and in case we were
|
// the result of the dictionary being (un)checked, and in case we were
|
||||||
// in solo, now we would end up with no dictionaries being checked at all.
|
// in solo, now we would end up with no dictionaries being checked at all.
|
||||||
for ( QList< QAction * >::iterator i = dictActions.begin(); i != dictActions.end(); ++i ) {
|
for ( const auto & dictAction : dictActions ) {
|
||||||
if ( ( *i )->isChecked() ) {
|
if ( dictAction->isChecked() ) {
|
||||||
isSolo = false;
|
isSolo = false;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if ( QApplication::keyboardModifiers() & Qt::ShiftModifier ) {
|
||||||
if ( isSolo ) {
|
if ( enterSoloMode ) {
|
||||||
// Restore or clear all the dictionaries
|
|
||||||
if ( QApplication::keyboardModifiers() & Qt::ShiftModifier )
|
|
||||||
*mutedDictionaries = storedMutedSet;
|
*mutedDictionaries = storedMutedSet;
|
||||||
else {
|
|
||||||
for ( QList< QAction * >::iterator i = dictActions.begin(); i != dictActions.end(); ++i )
|
|
||||||
mutedDictionaries->remove( ( *i )->data().toString() );
|
|
||||||
}
|
|
||||||
storedMutedSet.clear();
|
storedMutedSet.clear();
|
||||||
|
enterSoloMode = false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
// Save dictionaries state
|
// Save dictionaries state
|
||||||
|
if ( !enterSoloMode ) {
|
||||||
storedMutedSet = *mutedDictionaries;
|
storedMutedSet = *mutedDictionaries;
|
||||||
|
enterSoloMode = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( isSolo ) {
|
||||||
|
for ( const auto & dictAction : dictActions )
|
||||||
|
mutedDictionaries->remove( dictAction->data().toString() );
|
||||||
|
}
|
||||||
|
else {
|
||||||
// Make dictionary solo
|
// Make dictionary solo
|
||||||
for ( QList< QAction * >::iterator i = dictActions.begin(); i != dictActions.end(); ++i ) {
|
for ( const auto & dictAction : dictActions ) {
|
||||||
QString dictId = ( *i )->data().toString();
|
QString const dictId = dictAction->data().toString();
|
||||||
|
|
||||||
if ( dictId == id )
|
if ( dictId == id )
|
||||||
mutedDictionaries->remove( dictId );
|
mutedDictionaries->remove( dictId );
|
||||||
|
@ -274,6 +277,7 @@ void DictionaryBar::actionWasTriggered( QAction * action )
|
||||||
mutedDictionaries->insert( dictId );
|
mutedDictionaries->insert( dictId );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
configEvents.signalMutedDictionariesChanged();
|
configEvents.signalMutedDictionariesChanged();
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
|
@ -305,10 +309,10 @@ void DictionaryBar::dictsPaneClicked( const QString & id )
|
||||||
if ( !isVisible() )
|
if ( !isVisible() )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
for ( QList< QAction * >::iterator i = dictActions.begin(); i != dictActions.end(); ++i ) {
|
for ( const auto & dictAction : dictActions ) {
|
||||||
QString dictId = ( *i )->data().toString();
|
QString const dictId = dictAction->data().toString();
|
||||||
if ( dictId == id ) {
|
if ( dictId == id ) {
|
||||||
( *i )->activate( QAction::Trigger );
|
dictAction->activate( QAction::Trigger );
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -59,6 +59,8 @@ private:
|
||||||
Config::MutedDictionaries * mutedDictionaries;
|
Config::MutedDictionaries * mutedDictionaries;
|
||||||
Config::Events & configEvents;
|
Config::Events & configEvents;
|
||||||
Config::MutedDictionaries storedMutedSet;
|
Config::MutedDictionaries storedMutedSet;
|
||||||
|
|
||||||
|
bool enterSoloMode = false;
|
||||||
QString editDictionaryCommand;
|
QString editDictionaryCommand;
|
||||||
// how many dictionaries should be shown in the context menu:
|
// how many dictionaries should be shown in the context menu:
|
||||||
unsigned short const & maxDictionaryRefsInContextMenu;
|
unsigned short const & maxDictionaryRefsInContextMenu;
|
||||||
|
|
|
@ -53,3 +53,16 @@
|
||||||
| F3 | Dictionaries dialog |
|
| F3 | Dictionaries dialog |
|
||||||
| F4 | GoldenDict preferences |
|
| F4 | GoldenDict preferences |
|
||||||
| F12 | Inspector |
|
| F12 | Inspector |
|
||||||
|
|
||||||
|
|
||||||
|
# Solo mode in the dictionary bar
|
||||||
|
Ctrl+Click, Enter solo mode, toggle between single & all dictionaries
|
||||||
|
Shift+Click, Exit solo mode, restore the previous dictionaries.
|
||||||
|
|
||||||
|
For example, there are 4 dictionaries A,B,C,D with ABC selected.
|
||||||
|
| Cases| Note|
|
||||||
|
|--------|--------|
|
||||||
|
| Ctrl+Click A|select A only|
|
||||||
|
| Ctrl+Click A, Ctrl+Click B | select B only|
|
||||||
|
| Ctrl+Click A, Ctrl+Click A | A,B,C,D selected(all dictionaries selected)|
|
||||||
|
| Ctrl+Click A, Shift+Click any dictionary| A,B,C selected |
|
||||||
|
|
Loading…
Reference in a new issue