input panel again
This commit is contained in:
parent
f8982e2177
commit
e195614654
|
|
@ -20,10 +20,10 @@
|
||||||
|
|
||||||
namespace
|
namespace
|
||||||
{
|
{
|
||||||
class InputContext : public QskInputContext
|
class InputContextFactory : public QskInputContextFactory
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
virtual QskTextPredictor* textPredictor( const QLocale& locale ) const
|
virtual QskTextPredictor* createPredictor( const QLocale& locale ) const
|
||||||
{
|
{
|
||||||
#if HUNSPELL
|
#if HUNSPELL
|
||||||
/*
|
/*
|
||||||
|
|
@ -34,7 +34,7 @@ namespace
|
||||||
return new QskHunspellTextPredictor();
|
return new QskHunspellTextPredictor();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
return QskInputContext::textPredictor( locale );
|
return QskInputContextFactory::createPredictor( locale );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
@ -94,7 +94,9 @@ QskPlatformInputContext::QskPlatformInputContext()
|
||||||
auto context = QskInputContext::instance();
|
auto context = QskInputContext::instance();
|
||||||
if ( context == nullptr )
|
if ( context == nullptr )
|
||||||
{
|
{
|
||||||
context = new InputContext();
|
context = new QskInputContext();
|
||||||
|
context->setFactory( new InputContextFactory() );
|
||||||
|
|
||||||
QskInputContext::setInstance( context );
|
QskInputContext::setInstance( context );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -307,15 +307,17 @@ int main( int argc, char* argv[] )
|
||||||
QskInputContext::setInputEngine( ... );
|
QskInputContext::setInputEngine( ... );
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
Window window;
|
Window window1;
|
||||||
window.setColor( "PapayaWhip" );
|
window1.setObjectName( "Window 1" );
|
||||||
window.resize( 600, 600 );
|
window1.setColor( "PapayaWhip" );
|
||||||
window.show();
|
window1.resize( 600, 600 );
|
||||||
|
window1.show();
|
||||||
|
|
||||||
#if 0
|
#if 0
|
||||||
Window window2;
|
Window window2;
|
||||||
|
window2.setObjectName( "Window 2" );
|
||||||
window2.setColor( "Pink" );
|
window2.setColor( "Pink" );
|
||||||
window2.setX( window.x() + 100 );
|
window2.setX( window1.x() + 100 );
|
||||||
window2.resize( 600, 600 );
|
window2.resize( 600, 600 );
|
||||||
window2.show();
|
window2.show();
|
||||||
#endif
|
#endif
|
||||||
|
|
|
||||||
|
|
@ -8,7 +8,7 @@
|
||||||
#include <QskDialogButtonBox.h>
|
#include <QskDialogButtonBox.h>
|
||||||
#include <QskDialogButton.h>
|
#include <QskDialogButton.h>
|
||||||
#include <QskFocusIndicator.h>
|
#include <QskFocusIndicator.h>
|
||||||
#include <QskInputPanel.h>
|
#include <QskInputPanelBox.h>
|
||||||
#include <QskListView.h>
|
#include <QskListView.h>
|
||||||
#include <QskPageIndicator.h>
|
#include <QskPageIndicator.h>
|
||||||
#include <QskPushButton.h>
|
#include <QskPushButton.h>
|
||||||
|
|
@ -547,7 +547,7 @@ void QskMaterialSkin::initTabViewHints()
|
||||||
void QskMaterialSkin::initInputPanelHints()
|
void QskMaterialSkin::initInputPanelHints()
|
||||||
{
|
{
|
||||||
using namespace QskAspect;
|
using namespace QskAspect;
|
||||||
using Q = QskInputPanel;
|
using Q = QskInputPanelBox;
|
||||||
|
|
||||||
const ColorPalette& pal = m_data->palette;
|
const ColorPalette& pal = m_data->palette;
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -17,7 +17,7 @@
|
||||||
#include <QskTabButton.h>
|
#include <QskTabButton.h>
|
||||||
#include <QskTabBar.h>
|
#include <QskTabBar.h>
|
||||||
#include <QskTabView.h>
|
#include <QskTabView.h>
|
||||||
#include <QskInputPanel.h>
|
#include <QskInputPanelBox.h>
|
||||||
#include <QskInputPredictionBar.h>
|
#include <QskInputPredictionBar.h>
|
||||||
#include <QskVirtualKeyboard.h>
|
#include <QskVirtualKeyboard.h>
|
||||||
#include <QskScrollView.h>
|
#include <QskScrollView.h>
|
||||||
|
|
@ -618,7 +618,7 @@ void QskSquiekSkin::initTabViewHints()
|
||||||
void QskSquiekSkin::initInputPanelHints()
|
void QskSquiekSkin::initInputPanelHints()
|
||||||
{
|
{
|
||||||
using namespace QskAspect;
|
using namespace QskAspect;
|
||||||
using Q = QskInputPanel;
|
using Q = QskInputPanelBox;
|
||||||
|
|
||||||
setMargins( Q::Panel | Padding, 5 );
|
setMargins( Q::Panel | Padding, 5 );
|
||||||
setPanel( Q::Panel, Raised );
|
setPanel( Q::Panel, Raised );
|
||||||
|
|
|
||||||
|
|
@ -4,8 +4,8 @@
|
||||||
*****************************************************************************/
|
*****************************************************************************/
|
||||||
|
|
||||||
#include "QskInputContext.h"
|
#include "QskInputContext.h"
|
||||||
#include "QskInputEngine.h"
|
|
||||||
#include "QskInputPanel.h"
|
#include "QskInputPanel.h"
|
||||||
|
#include "QskInputPanelBox.h"
|
||||||
|
|
||||||
#include "QskLinearBox.h"
|
#include "QskLinearBox.h"
|
||||||
#include "QskDialog.h"
|
#include "QskDialog.h"
|
||||||
|
|
@ -26,54 +26,51 @@ QSK_QT_PRIVATE_END
|
||||||
|
|
||||||
namespace
|
namespace
|
||||||
{
|
{
|
||||||
class InputEngine final : public QskInputEngine
|
class Panel final : public QskInputPanel
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
virtual void attachToPanel( QQuickItem* item ) override
|
Panel( QQuickItem* parent = nullptr ):
|
||||||
|
QskInputPanel( parent )
|
||||||
{
|
{
|
||||||
if ( m_panel )
|
setAutoLayoutChildren( true );
|
||||||
m_panel->attachInputItem( item );
|
|
||||||
|
m_box = new QskInputPanelBox( this );
|
||||||
|
|
||||||
|
connect( m_box, &QskInputPanelBox::keySelected,
|
||||||
|
this, &QskInputPanel::keySelected );
|
||||||
|
|
||||||
|
connect( m_box, &QskInputPanelBox::predictiveTextSelected,
|
||||||
|
this, &QskInputPanel::predictiveTextSelected );
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual QskControl* createPanel() override
|
virtual void attachItem( QQuickItem* item ) override
|
||||||
{
|
{
|
||||||
m_panel = new QskInputPanel();
|
m_box->attachInputItem( item );
|
||||||
|
|
||||||
connect( m_panel, &QskInputPanel::keySelected,
|
|
||||||
this, &QskInputEngine::commitKey, Qt::UniqueConnection );
|
|
||||||
|
|
||||||
connect( m_panel, &QskInputPanel::predictiveTextSelected,
|
|
||||||
this, &QskInputEngine::commitPredictiveText, Qt::UniqueConnection );
|
|
||||||
|
|
||||||
return m_panel;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual QQuickItem* inputProxy() const override
|
virtual QQuickItem* inputProxy() const override
|
||||||
{
|
{
|
||||||
if ( m_panel )
|
return m_box->inputProxy();
|
||||||
{
|
|
||||||
if ( m_panel->panelHints() & QskInputPanel::InputProxy )
|
|
||||||
return m_panel->inputProxy();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return nullptr;
|
virtual void setPrompt( const QString& prompt ) override
|
||||||
|
{
|
||||||
|
m_box->setInputPrompt( prompt );
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void setPredictionEnabled( bool on ) override
|
virtual void setPredictionEnabled( bool on ) override
|
||||||
{
|
{
|
||||||
if ( m_panel )
|
m_box->setPanelHint( QskInputPanelBox::Prediction, on );
|
||||||
m_panel->setPanelHint( QskInputPanel::Prediction, on );
|
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void showPrediction( const QStringList& prediction ) override
|
virtual void setPrediction( const QStringList& prediction ) override
|
||||||
{
|
{
|
||||||
if ( m_panel )
|
m_box->setPrediction( prediction );
|
||||||
m_panel->setPrediction( prediction );
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
QPointer< QskInputPanel > m_panel;
|
QskInputPanelBox* m_box;
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static QPointer< QskInputContext > qskInputContext = nullptr;
|
static QPointer< QskInputContext > qskInputContext = nullptr;
|
||||||
|
|
@ -121,56 +118,50 @@ class QskInputContext::PrivateData
|
||||||
public:
|
public:
|
||||||
// item receiving the input
|
// item receiving the input
|
||||||
QPointer< QQuickItem > inputItem;
|
QPointer< QQuickItem > inputItem;
|
||||||
|
QPointer< QskInputPanel > panel;
|
||||||
|
|
||||||
// popup or window embedding the panel
|
// popup or window embedding the panel
|
||||||
QskPopup* inputPopup = nullptr;
|
QskPopup* inputPopup = nullptr;
|
||||||
QskWindow* inputWindow = nullptr;
|
QskWindow* inputWindow = nullptr;
|
||||||
|
|
||||||
QPointer< QskInputEngine > inputEngine;
|
QPointer< QskInputContextFactory > factory;
|
||||||
};
|
};
|
||||||
|
|
||||||
QskInputContext::QskInputContext():
|
QskInputContext::QskInputContext():
|
||||||
m_data( new PrivateData() )
|
m_data( new PrivateData() )
|
||||||
{
|
{
|
||||||
setObjectName( "InputContext" );
|
setObjectName( "InputContext" );
|
||||||
setEngine( new InputEngine() );
|
|
||||||
}
|
}
|
||||||
|
|
||||||
QskInputContext::~QskInputContext()
|
QskInputContext::~QskInputContext()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputContext::setEngine( QskInputEngine* engine )
|
void QskInputContext::setFactory( QskInputContextFactory* factory )
|
||||||
{
|
{
|
||||||
if ( m_data->inputEngine == engine )
|
if ( m_data->factory == factory )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if ( m_data->inputEngine && m_data->inputEngine->parent() == this )
|
if ( m_data->factory && m_data->factory->parent() == this )
|
||||||
{
|
delete m_data->factory;
|
||||||
m_data->inputEngine->disconnect( this );
|
|
||||||
|
|
||||||
if ( m_data->inputEngine->parent() == this )
|
m_data->factory = factory;
|
||||||
delete m_data->inputEngine;
|
|
||||||
}
|
|
||||||
|
|
||||||
m_data->inputEngine = engine;
|
if ( factory && factory->parent() == nullptr )
|
||||||
|
factory->setParent( this );
|
||||||
if ( engine )
|
|
||||||
{
|
|
||||||
if ( engine->parent() == nullptr )
|
|
||||||
engine->setParent( this );
|
|
||||||
|
|
||||||
connect( engine, &QskInputEngine::activeChanged,
|
|
||||||
this, &QskInputContext::activeChanged );
|
|
||||||
|
|
||||||
connect( engine, &QskInputEngine::localeChanged,
|
|
||||||
this, [] { qskSendToPlatformContext( QEvent::LocaleChange ); } );
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
QskInputEngine* QskInputContext::engine() const
|
QskInputContextFactory* QskInputContext::factory() const
|
||||||
{
|
{
|
||||||
return m_data->inputEngine;
|
return m_data->factory;
|
||||||
|
}
|
||||||
|
|
||||||
|
QskTextPredictor* QskInputContext::textPredictor( const QLocale& locale )
|
||||||
|
{
|
||||||
|
if ( m_data->factory )
|
||||||
|
return m_data->factory->createPredictor( locale );
|
||||||
|
|
||||||
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
QQuickItem* QskInputContext::inputItem() const
|
QQuickItem* QskInputContext::inputItem() const
|
||||||
|
|
@ -178,19 +169,6 @@ QQuickItem* QskInputContext::inputItem() const
|
||||||
return m_data->inputItem;
|
return m_data->inputItem;
|
||||||
}
|
}
|
||||||
|
|
||||||
QskControl* QskInputContext::inputPanel() const
|
|
||||||
{
|
|
||||||
if ( m_data->inputEngine == nullptr )
|
|
||||||
return nullptr;
|
|
||||||
|
|
||||||
auto panel = m_data->inputEngine->panel( true );
|
|
||||||
|
|
||||||
if ( panel && panel->parent() != this )
|
|
||||||
panel->setParent( const_cast< QskInputContext* >( this ) );
|
|
||||||
|
|
||||||
return panel;
|
|
||||||
}
|
|
||||||
|
|
||||||
void QskInputContext::update( Qt::InputMethodQueries queries )
|
void QskInputContext::update( Qt::InputMethodQueries queries )
|
||||||
{
|
{
|
||||||
if ( queries & Qt::ImEnabled )
|
if ( queries & Qt::ImEnabled )
|
||||||
|
|
@ -205,8 +183,8 @@ void QskInputContext::update( Qt::InputMethodQueries queries )
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( m_data->inputEngine )
|
if ( m_data->panel )
|
||||||
m_data->inputEngine->updateInputPanel( queries );
|
m_data->panel->updateInputPanel( queries );
|
||||||
}
|
}
|
||||||
|
|
||||||
QRectF QskInputContext::panelRect() const
|
QRectF QskInputContext::panelRect() const
|
||||||
|
|
@ -217,7 +195,7 @@ QRectF QskInputContext::panelRect() const
|
||||||
return QRectF();
|
return QRectF();
|
||||||
}
|
}
|
||||||
|
|
||||||
QskPopup* QskInputContext::createEmbeddingPopup( QskControl* panel )
|
QskPopup* QskInputContext::createEmbeddingPopup( QskInputPanel* panel )
|
||||||
{
|
{
|
||||||
auto popup = new QskPopup();
|
auto popup = new QskPopup();
|
||||||
|
|
||||||
|
|
@ -228,10 +206,7 @@ QskPopup* QskInputContext::createEmbeddingPopup( QskControl* panel )
|
||||||
auto box = new QskLinearBox( popup );
|
auto box = new QskLinearBox( popup );
|
||||||
box->addItem( panel );
|
box->addItem( panel );
|
||||||
|
|
||||||
Qt::Alignment alignment = Qt::AlignVCenter;
|
const auto alignment = panel->alignment() & Qt::AlignVertical_Mask;
|
||||||
if ( m_data->inputEngine )
|
|
||||||
alignment = m_data->inputEngine->panelAlignment() & Qt::AlignVertical_Mask;
|
|
||||||
|
|
||||||
popup->setOverlay( alignment == Qt::AlignVCenter );
|
popup->setOverlay( alignment == Qt::AlignVCenter );
|
||||||
|
|
||||||
switch( alignment )
|
switch( alignment )
|
||||||
|
|
@ -257,7 +232,7 @@ QskPopup* QskInputContext::createEmbeddingPopup( QskControl* panel )
|
||||||
return popup;
|
return popup;
|
||||||
}
|
}
|
||||||
|
|
||||||
QskWindow* QskInputContext::createEmbeddingWindow( QskControl* panel )
|
QskWindow* QskInputContext::createEmbeddingWindow( QskInputPanel* panel )
|
||||||
{
|
{
|
||||||
auto window = new QskWindow();
|
auto window = new QskWindow();
|
||||||
|
|
||||||
|
|
@ -273,18 +248,42 @@ QskWindow* QskInputContext::createEmbeddingWindow( QskControl* panel )
|
||||||
return window;
|
return window;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void QskInputContext::ensurePanel()
|
||||||
|
{
|
||||||
|
if ( m_data->panel )
|
||||||
|
return;
|
||||||
|
|
||||||
|
QskInputPanel* panel = nullptr;
|
||||||
|
|
||||||
|
if ( m_data->factory )
|
||||||
|
panel = m_data->factory->createPanel();
|
||||||
|
|
||||||
|
if ( panel == nullptr )
|
||||||
|
panel = new Panel();
|
||||||
|
|
||||||
|
panel->setParent( const_cast< QskInputContext* >( this ) );
|
||||||
|
|
||||||
|
connect( panel, &QskInputPanel::visibleChanged,
|
||||||
|
this, &QskInputContext::activeChanged,
|
||||||
|
Qt::UniqueConnection );
|
||||||
|
|
||||||
|
connect( panel, &QskInputPanel::localeChanged,
|
||||||
|
this, [] { qskSendToPlatformContext( QEvent::LocaleChange ); },
|
||||||
|
Qt::UniqueConnection );
|
||||||
|
|
||||||
|
m_data->panel = panel;
|
||||||
|
}
|
||||||
|
|
||||||
void QskInputContext::showPanel()
|
void QskInputContext::showPanel()
|
||||||
{
|
{
|
||||||
auto focusItem = qobject_cast< QQuickItem* >( qGuiApp->focusObject() );
|
auto focusItem = qobject_cast< QQuickItem* >( qGuiApp->focusObject() );
|
||||||
if ( focusItem == nullptr )
|
if ( focusItem == nullptr )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
auto panel = inputPanel();
|
ensurePanel();
|
||||||
if ( panel == nullptr )
|
|
||||||
return;
|
|
||||||
|
|
||||||
if ( ( focusItem == panel )
|
if ( ( focusItem == m_data->panel )
|
||||||
|| qskIsAncestorOf( panel, focusItem ) )
|
|| qskIsAncestorOf( m_data->panel, focusItem ) )
|
||||||
{
|
{
|
||||||
// ignore: usually the input proxy of the panel
|
// ignore: usually the input proxy of the panel
|
||||||
return;
|
return;
|
||||||
|
|
@ -300,7 +299,7 @@ void QskInputContext::showPanel()
|
||||||
|
|
||||||
if ( m_data->inputWindow == nullptr )
|
if ( m_data->inputWindow == nullptr )
|
||||||
{
|
{
|
||||||
auto window = createEmbeddingWindow( panel );
|
auto window = createEmbeddingWindow( m_data->panel );
|
||||||
|
|
||||||
if ( window )
|
if ( window )
|
||||||
{
|
{
|
||||||
|
|
@ -329,7 +328,7 @@ void QskInputContext::showPanel()
|
||||||
|
|
||||||
if ( m_data->inputPopup == nullptr )
|
if ( m_data->inputPopup == nullptr )
|
||||||
{
|
{
|
||||||
auto popup = createEmbeddingPopup( panel );
|
auto popup = createEmbeddingPopup( m_data->panel );
|
||||||
|
|
||||||
if ( popup )
|
if ( popup )
|
||||||
{
|
{
|
||||||
|
|
@ -345,8 +344,7 @@ void QskInputContext::showPanel()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( m_data->inputEngine )
|
m_data->panel->attachInputItem( m_data->inputItem );
|
||||||
m_data->inputEngine->attachInputItem( m_data->inputItem );
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputContext::hidePanel()
|
void QskInputContext::hidePanel()
|
||||||
|
|
@ -368,12 +366,12 @@ void QskInputContext::hidePanel()
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( m_data->inputEngine )
|
if ( m_data->panel )
|
||||||
{
|
{
|
||||||
if ( auto panel = m_data->inputEngine->panel( false ) )
|
m_data->panel->setParentItem( nullptr );
|
||||||
panel->setParentItem( nullptr );
|
m_data->panel->disconnect( this );
|
||||||
|
|
||||||
m_data->inputEngine->attachInputItem( nullptr );
|
m_data->panel->attachInputItem( nullptr );
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( m_data->inputPopup )
|
if ( m_data->inputPopup )
|
||||||
|
|
@ -410,11 +408,8 @@ bool QskInputContext::isActive() const
|
||||||
|
|
||||||
QLocale QskInputContext::locale() const
|
QLocale QskInputContext::locale() const
|
||||||
{
|
{
|
||||||
if ( m_data->inputEngine )
|
if ( m_data->panel )
|
||||||
{
|
return m_data->panel->locale();
|
||||||
if ( auto panel = m_data->inputEngine->panel( false ) )
|
|
||||||
return panel->locale();
|
|
||||||
}
|
|
||||||
|
|
||||||
return QLocale();
|
return QLocale();
|
||||||
}
|
}
|
||||||
|
|
@ -469,11 +464,6 @@ void QskInputContext::setFocusObject( QObject* focusObject )
|
||||||
m_data->inputItem = nullptr;
|
m_data->inputItem = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
QskTextPredictor* QskInputContext::textPredictor( const QLocale& ) const
|
|
||||||
{
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
void QskInputContext::processClickAt( int cursorPosition )
|
void QskInputContext::processClickAt( int cursorPosition )
|
||||||
{
|
{
|
||||||
Q_UNUSED( cursorPosition );
|
Q_UNUSED( cursorPosition );
|
||||||
|
|
@ -484,7 +474,7 @@ void QskInputContext::commitPrediction( bool )
|
||||||
/*
|
/*
|
||||||
called, when the input item loses the focus.
|
called, when the input item loses the focus.
|
||||||
As it it should be possible to navigate inside of the
|
As it it should be possible to navigate inside of the
|
||||||
inputPanel what should we do here ?
|
panel what should we do here ?
|
||||||
*/
|
*/
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -501,8 +491,8 @@ bool QskInputContext::eventFilter( QObject* object, QEvent* event )
|
||||||
}
|
}
|
||||||
case QEvent::Resize:
|
case QEvent::Resize:
|
||||||
{
|
{
|
||||||
if ( auto panel = inputPanel() )
|
if ( m_data->panel )
|
||||||
panel->setSize( m_data->inputWindow->size() );
|
m_data->panel->setSize( m_data->inputWindow->size() );
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
@ -535,4 +525,23 @@ bool QskInputContext::eventFilter( QObject* object, QEvent* event )
|
||||||
return Inherited::eventFilter( object, event );
|
return Inherited::eventFilter( object, event );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QskInputContextFactory::QskInputContextFactory( QObject* parent ):
|
||||||
|
QObject( parent )
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
QskInputContextFactory::~QskInputContextFactory()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
QskTextPredictor* QskInputContextFactory::createPredictor( const QLocale& ) const
|
||||||
|
{
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
QskInputPanel* QskInputContextFactory::createPanel() const
|
||||||
|
{
|
||||||
|
return new Panel();
|
||||||
|
}
|
||||||
|
|
||||||
#include "moc_QskInputContext.cpp"
|
#include "moc_QskInputContext.cpp"
|
||||||
|
|
|
||||||
|
|
@ -12,12 +12,24 @@
|
||||||
#include <memory>
|
#include <memory>
|
||||||
|
|
||||||
class QskTextPredictor;
|
class QskTextPredictor;
|
||||||
class QskControl;
|
class QskInputPanel;
|
||||||
class QskInputEngine;
|
class QskInputEngine;
|
||||||
class QskPopup;
|
class QskPopup;
|
||||||
class QskWindow;
|
class QskWindow;
|
||||||
class QQuickItem;
|
class QQuickItem;
|
||||||
|
|
||||||
|
class QSK_EXPORT QskInputContextFactory : public QObject
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
|
||||||
|
public:
|
||||||
|
QskInputContextFactory( QObject* parent = nullptr );
|
||||||
|
virtual ~QskInputContextFactory();
|
||||||
|
|
||||||
|
virtual QskTextPredictor* createPredictor( const QLocale& ) const;
|
||||||
|
virtual QskInputPanel* createPanel() const;
|
||||||
|
};
|
||||||
|
|
||||||
class QSK_EXPORT QskInputContext : public QObject
|
class QSK_EXPORT QskInputContext : public QObject
|
||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
|
@ -28,8 +40,8 @@ public:
|
||||||
QskInputContext();
|
QskInputContext();
|
||||||
virtual ~QskInputContext();
|
virtual ~QskInputContext();
|
||||||
|
|
||||||
void setEngine( QskInputEngine* );
|
void setFactory( QskInputContextFactory* );
|
||||||
QskInputEngine* engine() const;
|
QskInputContextFactory* factory() const;
|
||||||
|
|
||||||
QRectF panelRect() const;
|
QRectF panelRect() const;
|
||||||
|
|
||||||
|
|
@ -43,7 +55,7 @@ public:
|
||||||
static QskInputContext* instance();
|
static QskInputContext* instance();
|
||||||
static void setInstance( QskInputContext* );
|
static void setInstance( QskInputContext* );
|
||||||
|
|
||||||
virtual QskTextPredictor* textPredictor( const QLocale& ) const;
|
QskTextPredictor* textPredictor( const QLocale& locale );
|
||||||
|
|
||||||
Q_SIGNALS:
|
Q_SIGNALS:
|
||||||
void activeChanged();
|
void activeChanged();
|
||||||
|
|
@ -52,14 +64,12 @@ Q_SIGNALS:
|
||||||
protected:
|
protected:
|
||||||
virtual bool eventFilter( QObject*, QEvent* ) override;
|
virtual bool eventFilter( QObject*, QEvent* ) override;
|
||||||
|
|
||||||
virtual QskPopup* createEmbeddingPopup( QskControl* );
|
virtual QskPopup* createEmbeddingPopup( QskInputPanel* );
|
||||||
virtual QskWindow* createEmbeddingWindow( QskControl* );
|
virtual QskWindow* createEmbeddingWindow( QskInputPanel* );
|
||||||
|
|
||||||
virtual void showPanel();
|
virtual void showPanel();
|
||||||
virtual void hidePanel();
|
virtual void hidePanel();
|
||||||
|
|
||||||
QskControl* inputPanel() const;
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
friend class QskPlatformInputContext;
|
friend class QskPlatformInputContext;
|
||||||
|
|
||||||
|
|
@ -69,6 +79,8 @@ private:
|
||||||
virtual void processClickAt( int cursorPosition );
|
virtual void processClickAt( int cursorPosition );
|
||||||
virtual void commitPrediction( bool );
|
virtual void commitPrediction( bool );
|
||||||
|
|
||||||
|
void ensurePanel();
|
||||||
|
|
||||||
class PrivateData;
|
class PrivateData;
|
||||||
std::unique_ptr< PrivateData > m_data;
|
std::unique_ptr< PrivateData > m_data;
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -3,18 +3,27 @@
|
||||||
* This file may be used under the terms of the QSkinny License, Version 1.0
|
* This file may be used under the terms of the QSkinny License, Version 1.0
|
||||||
*****************************************************************************/
|
*****************************************************************************/
|
||||||
|
|
||||||
#include "QskInputEngine.h"
|
#include "QskInputPanel.h"
|
||||||
#include "QskInputContext.h"
|
#include "QskInputContext.h"
|
||||||
#include "QskTextPredictor.h"
|
#include "QskTextPredictor.h"
|
||||||
#include "QskControl.h"
|
|
||||||
|
|
||||||
#include <QPointer>
|
#include <QPointer>
|
||||||
#include <QTextCharFormat>
|
#include <QTextCharFormat>
|
||||||
|
|
||||||
static inline QQuickItem* qskReceiverItem( const QskInputEngine* engine )
|
static inline QQuickItem* qskReceiverItem( const QskInputPanel* panel )
|
||||||
{
|
{
|
||||||
auto item = engine->inputProxy();
|
if ( auto item = panel->inputProxy() )
|
||||||
return item ? item : engine->inputItem();
|
return item;
|
||||||
|
|
||||||
|
return panel->inputItem();
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline bool qskUsePrediction( Qt::InputMethodHints hints )
|
||||||
|
{
|
||||||
|
constexpr Qt::InputMethodHints mask =
|
||||||
|
Qt::ImhNoPredictiveText | Qt::ImhExclusiveInputMask | Qt::ImhHiddenText;
|
||||||
|
|
||||||
|
return ( hints & mask ) == 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline void qskSendReplaceText( QQuickItem* receiver, const QString& text )
|
static inline void qskSendReplaceText( QQuickItem* receiver, const QString& text )
|
||||||
|
|
@ -73,55 +82,21 @@ static inline void qskSendKey( QQuickItem* receiver, int key )
|
||||||
QCoreApplication::sendEvent( receiver, &keyRelease );
|
QCoreApplication::sendEvent( receiver, &keyRelease );
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline bool qskUsePrediction( Qt::InputMethodHints hints )
|
|
||||||
{
|
|
||||||
constexpr Qt::InputMethodHints mask =
|
|
||||||
Qt::ImhNoPredictiveText | Qt::ImhExclusiveInputMask | Qt::ImhHiddenText;
|
|
||||||
|
|
||||||
return ( hints & mask ) == 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline QString qskKeyString( int keyCode )
|
|
||||||
{
|
|
||||||
// Special case entry codes here, else default to the symbol
|
|
||||||
switch ( keyCode )
|
|
||||||
{
|
|
||||||
case Qt::Key_Shift:
|
|
||||||
case Qt::Key_CapsLock:
|
|
||||||
case Qt::Key_Mode_switch:
|
|
||||||
case Qt::Key_Backspace:
|
|
||||||
case Qt::Key_Muhenkan:
|
|
||||||
return QString();
|
|
||||||
|
|
||||||
case Qt::Key_Return:
|
|
||||||
case Qt::Key_Kanji:
|
|
||||||
return QChar( QChar::CarriageReturn );
|
|
||||||
|
|
||||||
case Qt::Key_Space:
|
|
||||||
return QChar( QChar::Space );
|
|
||||||
|
|
||||||
default:
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
return QChar( keyCode );
|
|
||||||
}
|
|
||||||
|
|
||||||
namespace
|
namespace
|
||||||
{
|
{
|
||||||
class KeyProcessor
|
class KeyProcessor
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
class Result
|
struct Result
|
||||||
{
|
{
|
||||||
public:
|
|
||||||
int key = 0;
|
int key = 0;
|
||||||
|
|
||||||
QString text;
|
QString text;
|
||||||
bool isFinal = true;
|
bool isFinal = true;
|
||||||
};
|
};
|
||||||
|
|
||||||
Result processKey( int key, Qt::InputMethodHints inputHints,
|
Result processKey(
|
||||||
|
int key, Qt::InputMethodHints inputHints,
|
||||||
QskTextPredictor* predictor, int spaceLeft )
|
QskTextPredictor* predictor, int spaceLeft )
|
||||||
{
|
{
|
||||||
Result result;
|
Result result;
|
||||||
|
|
@ -183,7 +158,7 @@ namespace
|
||||||
{
|
{
|
||||||
if ( !m_preedit.isEmpty() && spaceLeft)
|
if ( !m_preedit.isEmpty() && spaceLeft)
|
||||||
{
|
{
|
||||||
m_preedit += qskKeyString( key );
|
m_preedit += keyString( key );
|
||||||
m_preedit = m_preedit.left( spaceLeft );
|
m_preedit = m_preedit.left( spaceLeft );
|
||||||
|
|
||||||
result.text = m_preedit;
|
result.text = m_preedit;
|
||||||
|
|
@ -206,7 +181,7 @@ namespace
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const QString text = qskKeyString( key );
|
const QString text = keyString( key );
|
||||||
|
|
||||||
if ( predictor )
|
if ( predictor )
|
||||||
{
|
{
|
||||||
|
|
@ -242,15 +217,40 @@ namespace
|
||||||
}
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
inline QString keyString( int keyCode ) const
|
||||||
|
{
|
||||||
|
// Special case entry codes here, else default to the symbol
|
||||||
|
switch ( keyCode )
|
||||||
|
{
|
||||||
|
case Qt::Key_Shift:
|
||||||
|
case Qt::Key_CapsLock:
|
||||||
|
case Qt::Key_Mode_switch:
|
||||||
|
case Qt::Key_Backspace:
|
||||||
|
case Qt::Key_Muhenkan:
|
||||||
|
return QString();
|
||||||
|
|
||||||
|
case Qt::Key_Return:
|
||||||
|
case Qt::Key_Kanji:
|
||||||
|
return QChar( QChar::CarriageReturn );
|
||||||
|
|
||||||
|
case Qt::Key_Space:
|
||||||
|
return QChar( QChar::Space );
|
||||||
|
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return QChar( keyCode );
|
||||||
|
}
|
||||||
|
|
||||||
QString m_preedit;
|
QString m_preedit;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
class QskInputEngine::PrivateData
|
class QskInputPanel::PrivateData
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
KeyProcessor keyProcessor;
|
KeyProcessor keyProcessor;
|
||||||
QPointer< QskControl > panel;
|
|
||||||
QPointer< QQuickItem > inputItem;
|
QPointer< QQuickItem > inputItem;
|
||||||
|
|
||||||
QLocale predictorLocale;
|
QLocale predictorLocale;
|
||||||
|
|
@ -260,17 +260,30 @@ public:
|
||||||
bool hasPredictorLocale = false;
|
bool hasPredictorLocale = false;
|
||||||
};
|
};
|
||||||
|
|
||||||
QskInputEngine::QskInputEngine( QObject* parent ):
|
QskInputPanel::QskInputPanel( QQuickItem* parent ):
|
||||||
Inherited( parent ),
|
Inherited( parent ),
|
||||||
m_data( new PrivateData() )
|
m_data( new PrivateData() )
|
||||||
{
|
{
|
||||||
|
setAutoLayoutChildren( true );
|
||||||
|
initSizePolicy( QskSizePolicy::Expanding, QskSizePolicy::Constrained );
|
||||||
|
|
||||||
|
connect( this, &QskInputPanel::keySelected,
|
||||||
|
this, &QskInputPanel::commitKey );
|
||||||
|
|
||||||
|
connect( this, &QskInputPanel::predictiveTextSelected,
|
||||||
|
this, &QskInputPanel::commitPredictiveText );
|
||||||
|
|
||||||
|
connect( this, &QskControl::localeChanged,
|
||||||
|
this, &QskInputPanel::updateLocale );
|
||||||
|
|
||||||
|
updateLocale( locale() );
|
||||||
}
|
}
|
||||||
|
|
||||||
QskInputEngine::~QskInputEngine()
|
QskInputPanel::~QskInputPanel()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputEngine::attachInputItem( QQuickItem* item )
|
void QskInputPanel::attachInputItem( QQuickItem* item )
|
||||||
{
|
{
|
||||||
if ( item == m_data->inputItem )
|
if ( item == m_data->inputItem )
|
||||||
return;
|
return;
|
||||||
|
|
@ -288,108 +301,65 @@ void QskInputEngine::attachInputItem( QQuickItem* item )
|
||||||
m_data->keyProcessor.reset();
|
m_data->keyProcessor.reset();
|
||||||
m_data->inputHints = 0;
|
m_data->inputHints = 0;
|
||||||
|
|
||||||
attachToPanel( item );
|
attachItem( item );
|
||||||
|
|
||||||
Qt::InputMethodQueries queries = Qt::ImQueryAll;
|
Qt::InputMethodQueries queries = Qt::ImQueryAll;
|
||||||
queries &= ~Qt::ImEnabled;
|
queries &= ~Qt::ImEnabled;
|
||||||
|
|
||||||
updateInputPanel( queries );
|
updateInputPanel( queries );
|
||||||
|
|
||||||
|
if ( inputProxy() )
|
||||||
|
{
|
||||||
|
// hiding the cursor in item
|
||||||
|
const QInputMethodEvent::Attribute attribute(
|
||||||
|
QInputMethodEvent::Cursor, 0, 0, QVariant() );
|
||||||
|
|
||||||
|
QInputMethodEvent event( QString(), { attribute } );
|
||||||
|
QCoreApplication::sendEvent( item, &event );
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
attachToPanel( nullptr );
|
attachItem( nullptr );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputEngine::updateInputPanel(
|
void QskInputPanel::updateInputPanel( Qt::InputMethodQueries queries )
|
||||||
Qt::InputMethodQueries queries )
|
|
||||||
{
|
{
|
||||||
auto item = inputItem();
|
if ( m_data->inputItem == nullptr )
|
||||||
if ( item == nullptr )
|
|
||||||
return;
|
return;
|
||||||
|
|
||||||
QInputMethodQueryEvent event( queries );
|
QInputMethodQueryEvent event( queries );
|
||||||
QCoreApplication::sendEvent( item, &event );
|
QCoreApplication::sendEvent( m_data->inputItem, &event );
|
||||||
|
|
||||||
if ( queries & Qt::ImHints )
|
if ( queries & Qt::ImHints )
|
||||||
{
|
{
|
||||||
m_data->inputHints = static_cast< Qt::InputMethodHints >(
|
m_data->inputHints = static_cast< Qt::InputMethodHints >(
|
||||||
event.value( Qt::ImHints ).toInt() );
|
event.value( Qt::ImHints ).toInt() );
|
||||||
|
|
||||||
updatePanel();
|
setPredictionEnabled(
|
||||||
|
m_data->predictor && qskUsePrediction( m_data->inputHints ) );
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( queries & Qt::ImPreferredLanguage )
|
if ( queries & Qt::ImPreferredLanguage )
|
||||||
{
|
{
|
||||||
if ( m_data->panel )
|
setLocale( event.value( Qt::ImPreferredLanguage ).toLocale() );
|
||||||
{
|
|
||||||
m_data->panel->setLocale(
|
|
||||||
event.value( Qt::ImPreferredLanguage ).toLocale() );
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
QskControl* QskInputEngine::panel( bool doCreate )
|
void QskInputPanel::updateLocale( const QLocale& locale )
|
||||||
{
|
|
||||||
if ( m_data->panel == nullptr && doCreate )
|
|
||||||
{
|
|
||||||
auto panel = createPanel();
|
|
||||||
|
|
||||||
connect( panel, &QQuickItem::visibleChanged,
|
|
||||||
this, &QskInputEngine::activeChanged );
|
|
||||||
|
|
||||||
connect( panel, &QskControl::localeChanged,
|
|
||||||
this, &QskInputEngine::updateLocale );
|
|
||||||
|
|
||||||
m_data->panel = panel;
|
|
||||||
updateLocale( m_data->panel->locale() );
|
|
||||||
}
|
|
||||||
|
|
||||||
return m_data->panel;
|
|
||||||
}
|
|
||||||
|
|
||||||
Qt::Alignment QskInputEngine::panelAlignment() const
|
|
||||||
{
|
|
||||||
/*
|
|
||||||
When we have an input proxy, we don't care if
|
|
||||||
the input item becomes hidden
|
|
||||||
*/
|
|
||||||
|
|
||||||
return inputProxy() ? Qt::AlignVCenter : Qt::AlignBottom;
|
|
||||||
}
|
|
||||||
|
|
||||||
void QskInputEngine::updateLocale( const QLocale& locale )
|
|
||||||
{
|
{
|
||||||
if ( !m_data->hasPredictorLocale || locale != m_data->predictorLocale )
|
if ( !m_data->hasPredictorLocale || locale != m_data->predictorLocale )
|
||||||
{
|
{
|
||||||
m_data->hasPredictorLocale = true;
|
m_data->hasPredictorLocale = true;
|
||||||
m_data->predictorLocale = locale;
|
m_data->predictorLocale = locale;
|
||||||
|
|
||||||
resetPredictor( locale );
|
resetPredictor( locale );
|
||||||
|
|
||||||
m_data->keyProcessor.reset();
|
m_data->keyProcessor.reset();
|
||||||
updatePanel();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Q_EMIT localeChanged();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputEngine::updatePanel()
|
void QskInputPanel::resetPredictor( const QLocale& locale )
|
||||||
{
|
|
||||||
setPredictionEnabled(
|
|
||||||
m_data->predictor && qskUsePrediction( m_data->inputHints ) );
|
|
||||||
}
|
|
||||||
|
|
||||||
QQuickItem* QskInputEngine::inputItem() const
|
|
||||||
{
|
|
||||||
return m_data->inputItem;
|
|
||||||
}
|
|
||||||
|
|
||||||
QQuickItem* QskInputEngine::inputProxy() const
|
|
||||||
{
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
void QskInputEngine::resetPredictor( const QLocale& locale )
|
|
||||||
{
|
{
|
||||||
auto predictor = QskInputContext::instance()->textPredictor( locale );
|
auto predictor = QskInputContext::instance()->textPredictor( locale );
|
||||||
|
|
||||||
|
|
@ -409,49 +379,22 @@ void QskInputEngine::resetPredictor( const QLocale& locale )
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
m_data->predictor = predictor;
|
||||||
|
|
||||||
if ( predictor )
|
if ( predictor )
|
||||||
{
|
{
|
||||||
if ( predictor->parent() == nullptr )
|
if ( predictor->parent() == nullptr )
|
||||||
predictor->setParent( this );
|
predictor->setParent( this );
|
||||||
|
|
||||||
connect( predictor, &QskTextPredictor::predictionChanged,
|
connect( predictor, &QskTextPredictor::predictionChanged,
|
||||||
this, &QskInputEngine::updatePrediction );
|
this, &QskInputPanel::updatePrediction );
|
||||||
}
|
}
|
||||||
|
|
||||||
m_data->predictor = predictor;
|
setPredictionEnabled(
|
||||||
|
predictor && qskUsePrediction( m_data->inputHints ) );
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputEngine::applyInput( bool success )
|
void QskInputPanel::commitPredictiveText( int index )
|
||||||
{
|
|
||||||
auto item = inputItem();
|
|
||||||
if ( item == nullptr )
|
|
||||||
return;
|
|
||||||
|
|
||||||
if ( success )
|
|
||||||
{
|
|
||||||
if ( auto proxy = inputProxy() )
|
|
||||||
{
|
|
||||||
const auto value = proxy->property( "text" );
|
|
||||||
if ( value.canConvert< QString >() )
|
|
||||||
qskSendReplaceText( item, value.toString() );
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
qskSendKey( item, success ? Qt::Key_Return : Qt::Key_Escape );
|
|
||||||
}
|
|
||||||
|
|
||||||
void QskInputEngine::applyText( const QString& text, bool isFinal )
|
|
||||||
{
|
|
||||||
qskSendText( qskReceiverItem( this ), text, isFinal );
|
|
||||||
}
|
|
||||||
|
|
||||||
void QskInputEngine::applyKey( int key )
|
|
||||||
{
|
|
||||||
// control keys like left/right
|
|
||||||
qskSendKey( qskReceiverItem( this ), key );
|
|
||||||
}
|
|
||||||
|
|
||||||
void QskInputEngine::commitPredictiveText( int index )
|
|
||||||
{
|
{
|
||||||
QString text;
|
QString text;
|
||||||
|
|
||||||
|
|
@ -463,33 +406,57 @@ void QskInputEngine::commitPredictiveText( int index )
|
||||||
|
|
||||||
m_data->keyProcessor.reset();
|
m_data->keyProcessor.reset();
|
||||||
|
|
||||||
showPrediction( QStringList() );
|
setPrediction( QStringList() );
|
||||||
applyText( text, true );
|
|
||||||
|
qskSendText( qskReceiverItem( this ), text, true );
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputEngine::updatePrediction()
|
void QskInputPanel::updatePrediction()
|
||||||
{
|
{
|
||||||
if ( m_data->predictor )
|
if ( m_data->predictor )
|
||||||
showPrediction( m_data->predictor->candidates() );
|
setPrediction( m_data->predictor->candidates() );
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputEngine::setPredictionEnabled( bool on )
|
QQuickItem* QskInputPanel::inputProxy() const
|
||||||
{
|
{
|
||||||
Q_UNUSED( on )
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputEngine::showPrediction( const QStringList& )
|
QQuickItem* QskInputPanel::inputItem() const
|
||||||
|
{
|
||||||
|
return m_data->inputItem;
|
||||||
|
}
|
||||||
|
|
||||||
|
void QskInputPanel::setPrompt( const QString& )
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputEngine::commitKey( int key )
|
void QskInputPanel::setPredictionEnabled( bool )
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void QskInputPanel::setPrediction( const QStringList& )
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
Qt::Alignment QskInputPanel::alignment() const
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
When we have an input proxy, we don't care if
|
||||||
|
the input item becomes hidden
|
||||||
|
*/
|
||||||
|
|
||||||
|
return inputProxy() ? Qt::AlignVCenter : Qt::AlignBottom;
|
||||||
|
}
|
||||||
|
|
||||||
|
void QskInputPanel::commitKey( int key )
|
||||||
{
|
{
|
||||||
int spaceLeft = -1;
|
int spaceLeft = -1;
|
||||||
|
|
||||||
if ( !( m_data->inputHints & Qt::ImhMultiLine ) )
|
if ( !( m_data->inputHints & Qt::ImhMultiLine ) )
|
||||||
{
|
{
|
||||||
QInputMethodQueryEvent event1( Qt::ImMaximumTextLength );
|
QInputMethodQueryEvent event1( Qt::ImMaximumTextLength );
|
||||||
QCoreApplication::sendEvent( inputItem(), &event1 );
|
QCoreApplication::sendEvent( m_data->inputItem, &event1 );
|
||||||
|
|
||||||
const int maxChars = event1.value( Qt::ImMaximumTextLength ).toInt();
|
const int maxChars = event1.value( Qt::ImMaximumTextLength ).toInt();
|
||||||
if ( maxChars >= 0 )
|
if ( maxChars >= 0 )
|
||||||
|
|
@ -509,30 +476,42 @@ void QskInputEngine::commitKey( int key )
|
||||||
const auto result = m_data->keyProcessor.processKey(
|
const auto result = m_data->keyProcessor.processKey(
|
||||||
key, m_data->inputHints, predictor, spaceLeft );
|
key, m_data->inputHints, predictor, spaceLeft );
|
||||||
|
|
||||||
if ( result.key )
|
|
||||||
{
|
|
||||||
switch( result.key )
|
switch( result.key )
|
||||||
{
|
{
|
||||||
|
case 0:
|
||||||
|
{
|
||||||
|
if ( !result.text.isEmpty() )
|
||||||
|
{
|
||||||
|
qskSendText( qskReceiverItem( this ),
|
||||||
|
result.text, result.isFinal );
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
case Qt::Key_Return:
|
case Qt::Key_Return:
|
||||||
{
|
{
|
||||||
applyInput( true );
|
if ( auto proxy = inputProxy() )
|
||||||
|
{
|
||||||
|
// using input method query instead
|
||||||
|
const auto value = proxy->property( "text" );
|
||||||
|
if ( value.canConvert< QString >() )
|
||||||
|
{
|
||||||
|
qskSendReplaceText( m_data->inputItem, value.toString() );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
qskSendKey( m_data->inputItem, result.key );
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case Qt::Key_Escape:
|
case Qt::Key_Escape:
|
||||||
{
|
{
|
||||||
applyInput( false );
|
qskSendKey( m_data->inputItem, result.key );
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
default:
|
default:
|
||||||
{
|
{
|
||||||
applyKey( result.key );
|
qskSendKey( qskReceiverItem( this ), result.key );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
else if ( !result.text.isEmpty() )
|
|
||||||
{
|
|
||||||
applyText( result.text, result.isFinal );
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#include "moc_QskInputEngine.cpp"
|
#include "moc_QskInputPanel.cpp"
|
||||||
|
|
|
||||||
|
|
@ -3,62 +3,55 @@
|
||||||
* This file may be used under the terms of the QSkinny License, Version 1.0
|
* This file may be used under the terms of the QSkinny License, Version 1.0
|
||||||
*****************************************************************************/
|
*****************************************************************************/
|
||||||
|
|
||||||
#ifndef QSK_INPUT_ENGINE_H
|
#ifndef QSK_INPUT_PANEL_H
|
||||||
#define QSK_INPUT_ENGINE_H
|
#define QSK_INPUT_PANEL_H
|
||||||
|
|
||||||
#include "QskGlobal.h"
|
#include "QskGlobal.h"
|
||||||
#include <QObject>
|
#include "QskControl.h"
|
||||||
#include <memory>
|
#include <memory>
|
||||||
|
|
||||||
class QskTextPredictor;
|
class QskTextPredictor;
|
||||||
class QskControl;
|
class QString;
|
||||||
class QQuickItem;
|
class QStringList;
|
||||||
class QLocale;
|
|
||||||
|
|
||||||
class QSK_EXPORT QskInputEngine : public QObject
|
class QSK_EXPORT QskInputPanel : public QskControl
|
||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
|
||||||
using Inherited = QObject;
|
using Inherited = QskControl;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
QskInputEngine( QObject* parent = nullptr );
|
QskInputPanel( QQuickItem* parent = nullptr );
|
||||||
virtual ~QskInputEngine() override;
|
virtual ~QskInputPanel() override;
|
||||||
|
|
||||||
virtual void attachInputItem( QQuickItem* );
|
void attachInputItem( QQuickItem* );
|
||||||
virtual void updateInputPanel( Qt::InputMethodQueries );
|
void updateInputPanel( Qt::InputMethodQueries );
|
||||||
|
|
||||||
QskControl* panel( bool doCreate );
|
|
||||||
virtual Qt::Alignment panelAlignment() const;
|
|
||||||
|
|
||||||
virtual QQuickItem* inputProxy() const;
|
virtual QQuickItem* inputProxy() const;
|
||||||
virtual QQuickItem* inputItem() const;
|
QQuickItem* inputItem() const;
|
||||||
|
|
||||||
|
virtual Qt::Alignment alignment() const;
|
||||||
|
|
||||||
public Q_SLOTS:
|
public Q_SLOTS:
|
||||||
void commitKey( int keyCode );
|
void commitKey( int keyCode );
|
||||||
void commitPredictiveText( int index );
|
void commitPredictiveText( int index );
|
||||||
|
|
||||||
Q_SIGNALS:
|
Q_SIGNALS:
|
||||||
void activeChanged();
|
void keySelected( int keyCode );
|
||||||
void localeChanged();
|
void predictiveTextSelected( int );
|
||||||
|
|
||||||
|
public Q_SLOTS:
|
||||||
|
virtual void setPrompt( const QString& );
|
||||||
|
virtual void setPrediction( const QStringList& );
|
||||||
|
virtual void setPredictionEnabled( bool );
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
virtual QskControl* createPanel() = 0;
|
virtual void attachItem( QQuickItem* ) = 0;
|
||||||
virtual void attachToPanel( QQuickItem* ) = 0;
|
|
||||||
|
|
||||||
virtual void setPredictionEnabled( bool on );
|
|
||||||
virtual void showPrediction( const QStringList& );
|
|
||||||
|
|
||||||
void applyInput( bool success );
|
|
||||||
void applyText( const QString&, bool isFinal );
|
|
||||||
void applyKey( int keyCode );
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void resetPredictor( const QLocale& );
|
void resetPredictor( const QLocale& );
|
||||||
void updatePrediction();
|
void updatePrediction();
|
||||||
|
|
||||||
void updatePanel();
|
|
||||||
|
|
||||||
void updateLocale( const QLocale& );
|
void updateLocale( const QLocale& );
|
||||||
|
|
||||||
class PrivateData;
|
class PrivateData;
|
||||||
|
|
|
||||||
|
|
@ -3,7 +3,7 @@
|
||||||
* This file may be used under the terms of the QSkinny License, Version 1.0
|
* This file may be used under the terms of the QSkinny License, Version 1.0
|
||||||
*****************************************************************************/
|
*****************************************************************************/
|
||||||
|
|
||||||
#include "QskInputPanel.h"
|
#include "QskInputPanelBox.h"
|
||||||
#include "QskVirtualKeyboard.h"
|
#include "QskVirtualKeyboard.h"
|
||||||
#include "QskInputPredictionBar.h"
|
#include "QskInputPredictionBar.h"
|
||||||
#include "QskTextInput.h"
|
#include "QskTextInput.h"
|
||||||
|
|
@ -13,18 +13,17 @@
|
||||||
#include <QString>
|
#include <QString>
|
||||||
#include <QLocale>
|
#include <QLocale>
|
||||||
#include <QPointer>
|
#include <QPointer>
|
||||||
#include <QInputMethodQueryEvent>
|
|
||||||
|
|
||||||
namespace
|
namespace
|
||||||
{
|
{
|
||||||
class TextInputProxy final : public QskTextInput
|
class TextInputProxy final : public QskTextInput
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
TextInputProxy( QskInputPanel* panel, QQuickItem* parentItem = nullptr ):
|
TextInputProxy( QskInputPanelBox* panelBox, QQuickItem* parentItem = nullptr ):
|
||||||
QskTextInput( parentItem ),
|
QskTextInput( parentItem ),
|
||||||
m_panel( panel )
|
m_panelBox( panelBox )
|
||||||
{
|
{
|
||||||
setObjectName( "InputPanelInputProxy" );
|
setObjectName( "InputBoxProxy" );
|
||||||
setFocusPolicy( Qt::NoFocus );
|
setFocusPolicy( Qt::NoFocus );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -32,10 +31,10 @@ namespace
|
||||||
QskAspect::Subcontrol subControl ) const override
|
QskAspect::Subcontrol subControl ) const override
|
||||||
{
|
{
|
||||||
if ( subControl == QskTextInput::Panel )
|
if ( subControl == QskTextInput::Panel )
|
||||||
return m_panel->effectiveSubcontrol( QskInputPanel::ProxyPanel );
|
return m_panelBox->effectiveSubcontrol( QskInputPanelBox::ProxyPanel );
|
||||||
|
|
||||||
if ( subControl == QskTextInput::Text )
|
if ( subControl == QskTextInput::Text )
|
||||||
return m_panel->effectiveSubcontrol( QskInputPanel::ProxyText );
|
return m_panelBox->effectiveSubcontrol( QskInputPanelBox::ProxyText );
|
||||||
|
|
||||||
return subControl;
|
return subControl;
|
||||||
}
|
}
|
||||||
|
|
@ -50,15 +49,15 @@ namespace
|
||||||
}
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
QskInputPanel* m_panel;
|
QskInputPanelBox* m_panelBox;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
QSK_SUBCONTROL( QskInputPanel, Panel )
|
QSK_SUBCONTROL( QskInputPanelBox, Panel )
|
||||||
QSK_SUBCONTROL( QskInputPanel, ProxyPanel )
|
QSK_SUBCONTROL( QskInputPanelBox, ProxyPanel )
|
||||||
QSK_SUBCONTROL( QskInputPanel, ProxyText )
|
QSK_SUBCONTROL( QskInputPanelBox, ProxyText )
|
||||||
|
|
||||||
class QskInputPanel::PrivateData
|
class QskInputPanelBox::PrivateData
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
QPointer< QQuickItem > inputItem;
|
QPointer< QQuickItem > inputItem;
|
||||||
|
|
@ -69,28 +68,25 @@ public:
|
||||||
QskInputPredictionBar* predictionBar;
|
QskInputPredictionBar* predictionBar;
|
||||||
QskVirtualKeyboard* keyboard;
|
QskVirtualKeyboard* keyboard;
|
||||||
|
|
||||||
int maxChars = -1;
|
QskInputPanelBox::PanelHints panelHints = QskInputPanelBox::InputProxy;
|
||||||
|
|
||||||
QskInputPanel::PanelHints panelHints = QskInputPanel::InputProxy;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
QskInputPanel::QskInputPanel( QQuickItem* parent ):
|
QskInputPanelBox::QskInputPanelBox( QQuickItem* parent ):
|
||||||
Inherited( parent ),
|
Inherited( parent ),
|
||||||
m_data( new PrivateData() )
|
m_data( new PrivateData() )
|
||||||
{
|
{
|
||||||
setAutoLayoutChildren( true );
|
setAutoLayoutChildren( true );
|
||||||
initSizePolicy( QskSizePolicy::Expanding, QskSizePolicy::Constrained );
|
|
||||||
|
|
||||||
m_data->prompt = new QskTextLabel();
|
m_data->prompt = new QskTextLabel();
|
||||||
m_data->prompt->setVisible( false );
|
m_data->prompt->setVisible( false );
|
||||||
|
|
||||||
m_data->inputProxy = new TextInputProxy( this, nullptr );
|
m_data->inputProxy = new TextInputProxy( this, nullptr );
|
||||||
m_data->inputProxy->setVisible(
|
m_data->inputProxy->setVisible(
|
||||||
m_data->panelHints & QskInputPanel::InputProxy );
|
m_data->panelHints & QskInputPanelBox::InputProxy );
|
||||||
|
|
||||||
m_data->predictionBar = new QskInputPredictionBar();
|
m_data->predictionBar = new QskInputPredictionBar();
|
||||||
m_data->predictionBar->setVisible(
|
m_data->predictionBar->setVisible(
|
||||||
m_data->panelHints & QskInputPanel::Prediction );
|
m_data->panelHints & QskInputPanelBox::Prediction );
|
||||||
|
|
||||||
m_data->keyboard = new QskVirtualKeyboard();
|
m_data->keyboard = new QskVirtualKeyboard();
|
||||||
|
|
||||||
|
|
@ -105,17 +101,17 @@ QskInputPanel::QskInputPanel( QQuickItem* parent ):
|
||||||
m_data->layout = layout;
|
m_data->layout = layout;
|
||||||
|
|
||||||
connect( m_data->predictionBar, &QskInputPredictionBar::predictiveTextSelected,
|
connect( m_data->predictionBar, &QskInputPredictionBar::predictiveTextSelected,
|
||||||
this, &QskInputPanel::predictiveTextSelected );
|
this, &QskInputPanelBox::predictiveTextSelected );
|
||||||
|
|
||||||
connect( m_data->keyboard, &QskVirtualKeyboard::keySelected,
|
connect( m_data->keyboard, &QskVirtualKeyboard::keySelected,
|
||||||
this, &QskInputPanel::keySelected );
|
this, &QskInputPanelBox::keySelected );
|
||||||
}
|
}
|
||||||
|
|
||||||
QskInputPanel::~QskInputPanel()
|
QskInputPanelBox::~QskInputPanelBox()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputPanel::setPanelHint( PanelHint hint, bool on )
|
void QskInputPanelBox::setPanelHint( PanelHint hint, bool on )
|
||||||
{
|
{
|
||||||
if ( on )
|
if ( on )
|
||||||
setPanelHints( m_data->panelHints | hint );
|
setPanelHints( m_data->panelHints | hint );
|
||||||
|
|
@ -123,17 +119,17 @@ void QskInputPanel::setPanelHint( PanelHint hint, bool on )
|
||||||
setPanelHints( m_data->panelHints & ~hint );
|
setPanelHints( m_data->panelHints & ~hint );
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputPanel::setPanelHints( PanelHints hints )
|
void QskInputPanelBox::setPanelHints( PanelHints hints )
|
||||||
{
|
{
|
||||||
if ( hints == m_data->panelHints )
|
if ( hints == m_data->panelHints )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
m_data->panelHints = hints;
|
m_data->panelHints = hints;
|
||||||
|
|
||||||
m_data->inputProxy->setVisible( hints & QskInputPanel::InputProxy );
|
m_data->inputProxy->setVisible( hints & QskInputPanelBox::InputProxy );
|
||||||
m_data->predictionBar->setVisible( hints & QskInputPanel::Prediction );
|
m_data->predictionBar->setVisible( hints & QskInputPanelBox::Prediction );
|
||||||
|
|
||||||
const bool showPrompt = ( hints & QskInputPanel::InputProxy )
|
const bool showPrompt = ( hints & QskInputPanelBox::InputProxy )
|
||||||
&& !m_data->prompt->text().isEmpty();
|
&& !m_data->prompt->text().isEmpty();
|
||||||
|
|
||||||
m_data->prompt->setVisible( showPrompt );
|
m_data->prompt->setVisible( showPrompt );
|
||||||
|
|
@ -141,12 +137,12 @@ void QskInputPanel::setPanelHints( PanelHints hints )
|
||||||
Q_EMIT panelHintsChanged();
|
Q_EMIT panelHintsChanged();
|
||||||
}
|
}
|
||||||
|
|
||||||
QskInputPanel::PanelHints QskInputPanel::panelHints() const
|
QskInputPanelBox::PanelHints QskInputPanelBox::panelHints() const
|
||||||
{
|
{
|
||||||
return m_data->panelHints;
|
return m_data->panelHints;
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputPanel::attachInputItem( QQuickItem* item )
|
void QskInputPanelBox::attachInputItem( QQuickItem* item )
|
||||||
{
|
{
|
||||||
if ( item == m_data->inputItem )
|
if ( item == m_data->inputItem )
|
||||||
return;
|
return;
|
||||||
|
|
@ -155,55 +151,51 @@ void QskInputPanel::attachInputItem( QQuickItem* item )
|
||||||
|
|
||||||
if ( item )
|
if ( item )
|
||||||
{
|
{
|
||||||
if ( m_data->panelHints & QskInputPanel::InputProxy )
|
if ( m_data->panelHints & QskInputPanelBox::InputProxy )
|
||||||
{
|
{
|
||||||
m_data->inputProxy->setupFrom( item );
|
m_data->inputProxy->setupFrom( item );
|
||||||
m_data->inputProxy->setEditing( true );
|
m_data->inputProxy->setEditing( true );
|
||||||
|
|
||||||
// hiding the cursor in item
|
|
||||||
const QInputMethodEvent::Attribute attribute(
|
|
||||||
QInputMethodEvent::Cursor, 0, 0, QVariant() );
|
|
||||||
|
|
||||||
QInputMethodEvent event( QString(), { attribute } );
|
|
||||||
QCoreApplication::sendEvent( item, &event );
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
QQuickItem* QskInputPanel::attachedInputItem() const
|
QQuickItem* QskInputPanelBox::attachedInputItem() const
|
||||||
{
|
{
|
||||||
return m_data->inputItem;
|
return m_data->inputItem;
|
||||||
}
|
}
|
||||||
|
|
||||||
QQuickItem* QskInputPanel::inputProxy() const
|
QQuickItem* QskInputPanelBox::inputProxy() const
|
||||||
{
|
{
|
||||||
|
if ( m_data->panelHints & QskInputPanelBox::InputProxy )
|
||||||
return m_data->inputProxy;
|
return m_data->inputProxy;
|
||||||
|
|
||||||
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
QskAspect::Subcontrol QskInputPanel::effectiveSubcontrol(
|
QskAspect::Subcontrol QskInputPanelBox::effectiveSubcontrol(
|
||||||
QskAspect::Subcontrol subControl ) const
|
QskAspect::Subcontrol subControl ) const
|
||||||
{
|
{
|
||||||
if( subControl == QskBox::Panel )
|
if( subControl == QskBox::Panel )
|
||||||
return QskInputPanel::Panel;
|
return QskInputPanelBox::Panel;
|
||||||
|
|
||||||
#if 1
|
#if 1
|
||||||
// TODO ...
|
// TODO ...
|
||||||
if( subControl == QskInputPanel::ProxyPanel )
|
if( subControl == QskInputPanelBox::ProxyPanel )
|
||||||
return QskTextInput::Panel;
|
return QskTextInput::Panel;
|
||||||
|
|
||||||
if( subControl == QskInputPanel::ProxyText )
|
if( subControl == QskInputPanelBox::ProxyText )
|
||||||
return QskTextInput::Text;
|
return QskTextInput::Text;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
return subControl;
|
return subControl;
|
||||||
}
|
}
|
||||||
|
|
||||||
QString QskInputPanel::inputPrompt() const
|
QString QskInputPanelBox::inputPrompt() const
|
||||||
{
|
{
|
||||||
return m_data->prompt->text();
|
return m_data->prompt->text();
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputPanel::setInputPrompt( const QString& text )
|
void QskInputPanelBox::setInputPrompt( const QString& text )
|
||||||
{
|
{
|
||||||
auto prompt = m_data->prompt;
|
auto prompt = m_data->prompt;
|
||||||
|
|
||||||
|
|
@ -211,19 +203,19 @@ void QskInputPanel::setInputPrompt( const QString& text )
|
||||||
{
|
{
|
||||||
prompt->setText( text );
|
prompt->setText( text );
|
||||||
|
|
||||||
if ( m_data->panelHints & QskInputPanel::InputProxy )
|
if ( m_data->panelHints & QskInputPanelBox::InputProxy )
|
||||||
prompt->setVisible( !text.isEmpty() );
|
prompt->setVisible( !text.isEmpty() );
|
||||||
|
|
||||||
Q_EMIT inputPromptChanged( text );
|
Q_EMIT inputPromptChanged( text );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputPanel::setPrediction( const QStringList& prediction )
|
void QskInputPanelBox::setPrediction( const QStringList& prediction )
|
||||||
{
|
{
|
||||||
m_data->predictionBar->setPrediction( prediction );
|
m_data->predictionBar->setPrediction( prediction );
|
||||||
}
|
}
|
||||||
|
|
||||||
void QskInputPanel::keyPressEvent( QKeyEvent* event )
|
void QskInputPanelBox::keyPressEvent( QKeyEvent* event )
|
||||||
{
|
{
|
||||||
int keyCode = -1;
|
int keyCode = -1;
|
||||||
|
|
||||||
|
|
@ -254,4 +246,4 @@ void QskInputPanel::keyPressEvent( QKeyEvent* event )
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#include "moc_QskInputPanel.cpp"
|
#include "moc_QskInputPanelBox.cpp"
|
||||||
|
|
|
||||||
|
|
@ -3,8 +3,8 @@
|
||||||
* This file may be used under the terms of the QSkinny License, Version 1.0
|
* This file may be used under the terms of the QSkinny License, Version 1.0
|
||||||
*****************************************************************************/
|
*****************************************************************************/
|
||||||
|
|
||||||
#ifndef QSK_INPUT_PANEL_H
|
#ifndef QSK_INPUT_PANEL_BOX_H
|
||||||
#define QSK_INPUT_PANEL_H
|
#define QSK_INPUT_PANEL_BOX_H
|
||||||
|
|
||||||
#include "QskGlobal.h"
|
#include "QskGlobal.h"
|
||||||
#include "QskBox.h"
|
#include "QskBox.h"
|
||||||
|
|
@ -14,7 +14,7 @@ class QskInputEngine;
|
||||||
class QString;
|
class QString;
|
||||||
class QLocale;
|
class QLocale;
|
||||||
|
|
||||||
class QSK_EXPORT QskInputPanel : public QskBox
|
class QSK_EXPORT QskInputPanelBox : public QskBox
|
||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
|
||||||
|
|
@ -38,8 +38,8 @@ public:
|
||||||
Q_ENUM( PanelHint )
|
Q_ENUM( PanelHint )
|
||||||
Q_DECLARE_FLAGS( PanelHints, PanelHint )
|
Q_DECLARE_FLAGS( PanelHints, PanelHint )
|
||||||
|
|
||||||
QskInputPanel( QQuickItem* parent = nullptr );
|
QskInputPanelBox( QQuickItem* parent = nullptr );
|
||||||
virtual ~QskInputPanel() override;
|
virtual ~QskInputPanelBox() override;
|
||||||
|
|
||||||
void attachInputItem( QQuickItem* );
|
void attachInputItem( QQuickItem* );
|
||||||
QQuickItem* attachedInputItem() const;
|
QQuickItem* attachedInputItem() const;
|
||||||
|
|
@ -75,7 +75,7 @@ private:
|
||||||
std::unique_ptr< PrivateData > m_data;
|
std::unique_ptr< PrivateData > m_data;
|
||||||
};
|
};
|
||||||
|
|
||||||
Q_DECLARE_OPERATORS_FOR_FLAGS( QskInputPanel::PanelHints )
|
Q_DECLARE_OPERATORS_FOR_FLAGS( QskInputPanelBox::PanelHints )
|
||||||
Q_DECLARE_METATYPE( QskInputPanel::PanelHints )
|
Q_DECLARE_METATYPE( QskInputPanelBox::PanelHints )
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
||||||
|
|
@ -300,15 +300,15 @@ SOURCES += \
|
||||||
SOURCES += \
|
SOURCES += \
|
||||||
inputpanel/QskTextPredictor.cpp \
|
inputpanel/QskTextPredictor.cpp \
|
||||||
inputpanel/QskInputContext.cpp \
|
inputpanel/QskInputContext.cpp \
|
||||||
inputpanel/QskInputEngine.cpp \
|
|
||||||
inputpanel/QskInputPanel.cpp \
|
inputpanel/QskInputPanel.cpp \
|
||||||
|
inputpanel/QskInputPanelBox.cpp \
|
||||||
inputpanel/QskInputPredictionBar.cpp \
|
inputpanel/QskInputPredictionBar.cpp \
|
||||||
inputpanel/QskVirtualKeyboard.cpp
|
inputpanel/QskVirtualKeyboard.cpp
|
||||||
|
|
||||||
HEADERS += \
|
HEADERS += \
|
||||||
inputpanel/QskTextPredictor.h \
|
inputpanel/QskTextPredictor.h \
|
||||||
inputpanel/QskInputContext.h \
|
inputpanel/QskInputContext.h \
|
||||||
inputpanel/QskInputEngine.h \
|
|
||||||
inputpanel/QskInputPanel.h \
|
inputpanel/QskInputPanel.h \
|
||||||
|
inputpanel/QskInputPanelBox.h \
|
||||||
inputpanel/QskInputPredictionBar.h \
|
inputpanel/QskInputPredictionBar.h \
|
||||||
inputpanel/QskVirtualKeyboard.h
|
inputpanel/QskVirtualKeyboard.h
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue