16#include <com/sun/star/configuration/theDefaultProvider.hpp>
17#include <com/sun/star/lang/XMultiServiceFactory.hpp>
18#include <com/sun/star/beans/NamedValue.hpp>
19#include <com/sun/star/beans/UnknownPropertyException.hpp>
20#include <com/sun/star/beans/XPropertySetInfo.hpp>
21#include <com/sun/star/container/XNameAccess.hpp>
22#include <com/sun/star/container/XNameReplace.hpp>
23#include <com/sun/star/container/XHierarchicalName.hpp>
24#include <com/sun/star/uno/Reference.hxx>
25#include <com/sun/star/uno/Type.hxx>
26#include <com/sun/star/uno/TypeClass.hpp>
27#include <com/sun/star/util/XChangesBatch.hpp>
28#include <com/sun/star/util/SearchFlags.hpp>
29#include <com/sun/star/util/SearchAlgorithms2.hpp>
31#include <rtl/ustrbuf.hxx>
46#define SHORT_LEN_LIMIT 7
47#define LONG_LEN_LIMIT 11
48#define HYPER_LEN_LIMIT 20
56 Prop_Impl( OUString sName, OUString sProperty, Any aValue )
66 OUString sPropertyPath;
70 explicit UserData( OUString aPropertyPath )
71 : bIsPropertyPath( true )
72 , sPropertyPath(
std::move(aPropertyPath))
77 : bIsPropertyPath( false )
79 , aXNameAccess( rXNameAccess )
86 bool bNonSpace = rKeyEvent.GetKeyCode().GetCode() !=
KEY_SPACE;
87 if (m_bNumericOnly && bNonSpace )
90 sal_uInt16 nGroup = rKeyCode.
GetGroup();
91 sal_uInt16 nKey = rKeyCode.
GetCode();
130 if ( !bValid && ( rKeyCode.
IsMod1() && (
142 : GenericDialogController(pParent,
"cui/ui/aboutconfigdialog.ui",
"AboutConfig")
143 , m_xResetBtn(m_xBuilder->weld_button(
"reset"))
144 , m_xEditBtn(m_xBuilder->weld_button(
"edit"))
145 , m_xSearchBtn(m_xBuilder->weld_button(
"searchButton"))
146 , m_xSearchEdit(m_xBuilder->weld_entry(
"searchEntry"))
147 , m_xPrefBox(m_xBuilder->weld_tree_view(
"preferences"))
148 , m_xScratchIter(m_xPrefBox->make_iterator())
164 util::SearchFlags::REG_NOT_ENDOFLINE);
166 float fWidth =
m_xPrefBox->get_approximate_digit_width();
167 std::vector<int> aWidths
169 o3tl::narrowing<int>(fWidth * 65),
170 o3tl::narrowing<int>(fWidth * 20),
171 o3tl::narrowing<int>(fWidth * 8)
180 m_xPrefBox->make_sorted();
184 bool bSortAtoZ = m_xPrefBox->get_sort_order();
187 if (nColumn == m_xPrefBox->get_sort_column())
189 bSortAtoZ = !bSortAtoZ;
190 m_xPrefBox->set_sort_order(bSortAtoZ);
194 int nOldSortColumn = m_xPrefBox->get_sort_column();
195 if (nOldSortColumn != -1)
197 m_xPrefBox->set_sort_column(nColumn);
212 const OUString& rType,
const OUString& rValue,
const weld::TreeIter* pParentEntry,
213 bool bInsertToPrefBox)
216 if (bInsertToPrefBox)
248 FillItems( xConfigAccess,
nullptr, 0,
true );
256 std::vector< std::shared_ptr< Prop_Impl > >::iterator pIter;
262 xNameReplace->replaceByName( (*pIter)->Property, (*pIter)->Value );
265 xChangesBatch->commitChanges();
270 int lineage,
bool bLoadAll)
273 xNameAccess, uno::UNO_QUERY_THROW )->getHierarchicalName();
275 for(
const OUString& item : seqItems )
277 Any aNode = xNameAccess->getByName( item );
279 bool bNotLeaf =
false;
284 xNextNameAccess.set(aNode, uno::UNO_QUERY);
285 bNotLeaf = xNextNameAccess.is();
295 FillItems(xNextNameAccess,
nullptr, lineage + 1,
true);
299 m_vectorUserData.push_back(std::make_unique<UserData>(xNextNameAccess, lineage + 1));
312 OUString sPropertyName = item;
314 [&sPath, &sPropertyName](
const prefBoxEntry& rEntry) ->
bool
316 return rEntry.pUserData->sPropertyPath == sPath
317 && rEntry.sStatus == sPropertyName;
321 OUString
sType = aNode.getValueTypeName();
322 OUStringBuffer sValue;
328 switch( aNode.getValueType().getTypeClass() )
330 case css::uno::TypeClass_VOID:
333 case css::uno::TypeClass_BOOLEAN:
334 sValue = OUString::boolean( aNode.get<
bool>() );
337 case css::uno::TypeClass_SHORT:
338 case css::uno::TypeClass_LONG:
339 case css::uno::TypeClass_HYPER:
340 sValue = OUString::number( aNode.get<sal_Int64>() );
343 case css::uno::TypeClass_DOUBLE:
344 sValue = OUString::number( aNode.get<
double>() );
347 case css::uno::TypeClass_STRING:
348 sValue = aNode.get<OUString>();
351 case css::uno::TypeClass_SEQUENCE:
352 if(
sType ==
"[]boolean" )
355 for( sal_Int32 j = 0; j != seq.getLength(); ++j )
361 sValue.append(OUString::boolean( seq[j] ));
364 else if(
sType ==
"[]byte" )
369 OUString s = OUString::number(
371 if( s.getLength() == 1 )
375 sValue.append(s.toAsciiUpperCase());
378 else if(
sType ==
"[][]byte" )
381 for( sal_Int32 j = 0; j != seq.getLength(); ++j )
389 OUString s = OUString::number(
391 if( s.getLength() == 1 )
395 sValue.append(s.toAsciiUpperCase());
399 else if(
sType ==
"[]short" )
402 for( sal_Int32 j = 0; j != seq.getLength(); ++j )
408 sValue.append(
static_cast<sal_Int32
>(seq[j]) );
411 else if(
sType ==
"[]long" )
414 for( sal_Int32 j = 0; j != seq.getLength(); ++j )
420 sValue.append( seq[j] );
423 else if(
sType ==
"[]hyper" )
426 for( sal_Int32 j = 0; j != seq.getLength(); ++j )
432 sValue.append( seq[j] );
435 else if(
sType ==
"[]double" )
438 for( sal_Int32 j = 0; j != seq.getLength(); ++j )
444 sValue.append( seq[j] );
447 else if(
sType ==
"[]string" )
450 for( sal_Int32 j = 0; j != seq.getLength(); ++j )
456 sValue.append(seq[j]);
463 "path \"" << sPath <<
"\" member " << item
464 <<
" of unsupported type " <<
sType);
471 "path \"" << sPath <<
"\" member " << item
472 <<
" of unsupported type " <<
sType);
479 for(
int j = 1; j < lineage; ++j)
482 InsertEntry(sPath, sPath.copy(
index+1), item,
sType, sValue.makeStringAndClear(), pParentEntry, !bLoadAll);
492 css::configuration::theDefaultProvider::get( xContext ) );
494 beans::NamedValue aProperty;
495 aProperty.Name =
"nodepath";
496 aProperty.Value <<= sNodePath;
500 OUString sAccessString;
503 sAccessString =
"com.sun.star.configuration.ConfigurationUpdateAccess";
505 sAccessString =
"com.sun.star.configuration.ConfigurationAccess";
508 xConfigProvider->createInstanceWithArguments(
509 sAccessString, aArgumentList ),
510 uno::UNO_QUERY_THROW );
517 bool isModifiedBefore =
false;
521 if( rProp->Name == nInd->Name && rProp->Property == nInd->Property )
526 isModifiedBefore =
true;
531 if( !isModifiedBefore )
538 std::vector<OUString> tempVector;
546 tempVector.push_back(word);
547 }
while(
index >= 0 );
552 const OUString& rValue,
554 : GenericDialogController(pWindow,
"cui/ui/aboutconfigvaluedialog.ui",
"AboutConfigValueDialog")
555 , m_bNumericOnly(limit != 0)
556 , m_xEDValue(m_xBuilder->weld_entry(
"valuebox"))
575 StandardHdl_Impl(*m_xEditBtn);
581 if (!m_xPrefBox->get_selected(m_xScratchIter.get()))
584 UserData *pUserData = weld::fromId<UserData*>(m_xPrefBox->get_id(*m_xScratchIter));
585 if (!(pUserData && pUserData->bIsPropertyPath))
589 OUString sPropertyName = m_xPrefBox->get_text(*m_xScratchIter, 1);
590 OUString sPropertyType = m_xPrefBox->get_text(*m_xScratchIter, 2);
591 OUString sPropertyValue = m_xPrefBox->get_text(*m_xScratchIter, 3);
594 if (sPropertyType ==
"void")
596 css::uno::Reference<css::beans::XPropertySetInfo> info(
598 css::uno::UNO_QUERY_THROW);
601 t = info->getPropertyByName(sPropertyName).Type;
602 }
catch (css::beans::UnknownPropertyException &) {
609 sPropertyType =
t.getTypeName();
610 switch (
t.getTypeClass()) {
611 case css::uno::TypeClass_BOOLEAN:
612 sPropertyValue =
"false";
614 case css::uno::TypeClass_SHORT:
615 case css::uno::TypeClass_LONG:
616 case css::uno::TypeClass_HYPER:
617 case css::uno::TypeClass_DOUBLE:
618 sPropertyValue =
"0";
626 auto pProperty = std::make_shared<Prop_Impl>( pUserData->sPropertyPath, sPropertyName,
Any( sPropertyValue ) );
627 bool bSaveChanges =
false;
629 bool bOpenDialog =
true;
630 OUString sDialogValue;
632 if( sPropertyType ==
"boolean" )
635 if( sPropertyValue ==
"true" )
637 sDialogValue =
"false";
642 sDialogValue =
"true";
646 pProperty->Value <<= bValue;
650 else if ( sPropertyType ==
"void" )
656 sDialogValue = sPropertyValue;
666 if( sPropertyType ==
"short" )
668 else if( sPropertyType ==
"long" )
670 else if( sPropertyType ==
"hyper" )
677 OUString sNewValue = aValueDialog.
getValue();
679 if ( sPropertyType ==
"short")
682 sal_Int32 nNumb = sNewValue.toInt32();
686 throw uno::Exception(
"out of range short",
nullptr);
687 nShort =
static_cast<sal_Int16
>(nNumb);
688 pProperty->Value <<= nShort;
690 else if( sPropertyType ==
"long" )
692 sal_Int32 nLong = sNewValue.toInt32();
693 if( nLong==0 && sNewValue.getLength()!=1)
694 throw uno::Exception(
"out of range long",
nullptr);
695 pProperty->Value <<= nLong;
697 else if( sPropertyType ==
"hyper")
699 sal_Int64 nHyper = sNewValue.toInt64();
700 if( nHyper==0 && sNewValue.getLength()!=1)
701 throw uno::Exception(
"out of range hyper",
nullptr);
702 pProperty->Value <<= nHyper;
704 else if( sPropertyType ==
"double")
706 double nDoub = sNewValue.toDouble();
707 if( nDoub ==0 && sNewValue.getLength()!=1)
708 throw uno::Exception(
"out of range double",
nullptr);
709 pProperty->Value <<= nDoub;
711 else if( sPropertyType ==
"float")
713 float nFloat = sNewValue.toFloat();
714 if( nFloat ==0 && sNewValue.getLength()!=1)
715 throw uno::Exception(
"out of range float",
nullptr);
716 pProperty->Value <<= nFloat;
718 else if( sPropertyType ==
"string" )
720 pProperty->Value <<= sNewValue;
722 else if( sPropertyType ==
"[]short" )
726 std::vector< OUString > seqStr = commaStringToSequence( sNewValue );
731 std::transform(seqStr.begin(), seqStr.end(), seqShort.getArray(),
733 { return static_cast<sal_Int16>(str.toInt32()); });
734 pProperty->Value <<= seqShort;
736 else if( sPropertyType ==
"[]long" )
738 std::vector< OUString > seqStrLong = commaStringToSequence( sNewValue );
741 std::transform(seqStrLong.begin(), seqStrLong.end(), seqLong.getArray(),
742 [](
const auto& str) { return str.toInt32(); });
743 pProperty->Value <<= seqLong;
745 else if( sPropertyType ==
"[]hyper" )
747 std::vector< OUString > seqStrHyper = commaStringToSequence( sNewValue );
749 std::transform(seqStrHyper.begin(), seqStrHyper.end(), seqHyper.getArray(),
750 [](
const auto& str) { return str.toInt64(); });
751 pProperty->Value <<= seqHyper;
753 else if( sPropertyType ==
"[]double" )
755 std::vector< OUString > seqStrDoub = commaStringToSequence( sNewValue );
757 std::transform(seqStrDoub.begin(), seqStrDoub.end(), seqDoub.getArray(),
758 [](
const auto& str) { return str.toDouble(); });
759 pProperty->Value <<= seqDoub;
761 else if( sPropertyType ==
"[]float" )
763 std::vector< OUString > seqStrFloat = commaStringToSequence( sNewValue );
765 std::transform(seqStrFloat.begin(), seqStrFloat.end(), seqFloat.getArray(),
766 [](
const auto& str) { return str.toFloat(); });
767 pProperty->Value <<= seqFloat;
769 else if( sPropertyType ==
"[]string" )
774 throw uno::Exception(
"unknown property type " + sPropertyType,
nullptr);
776 sDialogValue = sNewValue;
782 AddToModifiedVector( pProperty );
785 m_xPrefBox->set_text(*m_xScratchIter, sPropertyType, 2);
786 m_xPrefBox->set_text(*m_xScratchIter, sDialogValue, 3);
788 auto it = std::find_if(m_prefBoxEntries.begin(), m_prefBoxEntries.end(),
789 [&pUserData, &sPropertyName](
const prefBoxEntry& rEntry) ->
bool
791 return rEntry.pUserData->sPropertyPath == pUserData->sPropertyPath
792 && rEntry.sStatus == sPropertyName;
795 if (it != m_prefBoxEntries.end())
797 it->sValue = sDialogValue;
799 auto modifiedIt = std::find_if(
800 m_modifiedPrefBoxEntries.begin(), m_modifiedPrefBoxEntries.end(),
801 [&pUserData, &sPropertyName](
const prefBoxEntry& rEntry) ->
bool
803 return rEntry.pUserData->sPropertyPath == pUserData->sPropertyPath
804 && rEntry.sStatus == sPropertyName;
808 if (modifiedIt != m_modifiedPrefBoxEntries.end())
810 modifiedIt->sValue = sDialogValue;
814 m_modifiedPrefBoxEntries.push_back(*it);
819 catch( uno::Exception& )
830 m_xPrefBox->freeze();
833 m_xPrefBox->make_unsorted();
835 if (m_xSearchEdit->get_text().isEmpty())
839 FillItems( xConfigAccess );
843 m_options.searchString = m_xSearchEdit->get_text();
845 for (
auto const& it : m_prefBoxEntries)
847 sal_Int32 endPos, startPos = 0;
849 for(
size_t i = 0;
i < 5; ++
i)
854 scrTxt = it.pUserData->sPropertyPath;
864 endPos = scrTxt.getLength();
876 m_xPrefBox->make_sorted();
879 m_xPrefBox->expand_row(rEntry);
887 OUString sPathWithProperty = rEntry.
pUserData->sPropertyPath;
888 sal_Int32
index = sPathWithProperty.lastIndexOf(rEntry.
sProp);
889 OUString sPath = sPathWithProperty.copy(0,
index);
891 std::unique_ptr<weld::TreeIter> xParentEntry(
m_xPrefBox->make_iterator());
892 std::unique_ptr<weld::TreeIter> xGrandParentEntry;
896 int prevIndex =
index;
908 OUString sParentName = sPath.copy(prevIndex+1,
index - prevIndex - 1);
910 bool hasEntry =
false;
913 if (!xGrandParentEntry)
914 bStartOk =
m_xPrefBox->get_iter_first(*xParentEntry);
917 m_xPrefBox->copy_iterator(*xGrandParentEntry, *xParentEntry);
918 bStartOk =
m_xPrefBox->iter_children(*xParentEntry);
925 if (
m_xPrefBox->get_text(*xParentEntry, 0) == sParentName)
930 }
while (
m_xPrefBox->iter_next_sibling(*xParentEntry));
935 m_xPrefBox->insert(xGrandParentEntry.get(), -1, &sParentName,
nullptr,
nullptr,
nullptr,
false, xParentEntry.get());
942 xGrandParentEntry =
m_xPrefBox->make_iterator(xParentEntry.get());
943 }
while(
index < sPath.getLength() - 1);
954 if (m_xPrefBox->iter_has_child(rEntry))
956 UserData *pUserData = weld::fromId<UserData*>(m_xPrefBox->get_id(rEntry));
957 if (pUserData && !pUserData->bIsPropertyPath)
959 assert(pUserData->aXNameAccess.is());
960 FillItems(pUserData->aXNameAccess, &rEntry, pUserData->aLineage);
Reference< XExecutableDialog > m_xDialog
std::vector< prefBoxEntry > m_modifiedPrefBoxEntries
std::vector< std::unique_ptr< UserData > > m_vectorUserData
void FillItems(const css::uno::Reference< css::container::XNameAccess > &xNameAccess, const weld::TreeIter *pParentEntry=nullptr, int lineage=0, bool bLoadAll=false)
CuiAboutConfigTabPage(weld::Window *pParent)
void InsertEntry(const prefBoxEntry &rEntry)
std::vector< prefBoxEntry > m_prefBoxEntries
void AddToModifiedVector(const std::shared_ptr< Prop_Impl > &rProp)
std::vector< std::shared_ptr< Prop_Impl > > m_vectorOfModified
std::unique_ptr< weld::TreeView > m_xPrefBox
virtual ~CuiAboutConfigTabPage() override
static std::vector< OUString > commaStringToSequence(std::u16string_view rCommaSepString)
static css::uno::Reference< css::container::XNameAccess > getConfigAccess(const OUString &sNodePath, bool bUpdate)
std::unique_ptr< weld::Button > m_xSearchBtn
i18nutil::SearchOptions2 m_options
std::unique_ptr< weld::Button > m_xEditBtn
std::unique_ptr< weld::Button > m_xResetBtn
std::unique_ptr< weld::TreeIter > m_xScratchIter
virtual ~CuiAboutConfigValueDialog() override
std::unique_ptr< weld::Entry > m_xEDValue
CuiAboutConfigValueDialog(weld::Window *pWindow, const OUString &rValue, int limit)
OUString getValue() const
bool SearchForward(const OUString &rStr, sal_Int32 *pStart, sal_Int32 *pEnd, css::util::SearchResult *pRes=nullptr)
sal_uInt16 GetGroup() const
sal_uInt16 GetCode() const
std::shared_ptr< weld::Dialog > m_xDialog
#define TOOLS_WARN_EXCEPTION(area, stream)
constexpr sal_uInt16 KEY_X
constexpr sal_uInt16 KEY_V
constexpr sal_uInt16 KEY_EQUAL
constexpr sal_uInt16 KEY_COMMA
constexpr sal_uInt16 KEY_POINT
constexpr sal_uInt16 KEYGROUP_MISC
constexpr sal_uInt16 KEY_Z
constexpr sal_uInt16 KEY_A
constexpr sal_uInt16 KEY_SPACE
constexpr sal_uInt16 KEYGROUP_NUM
constexpr sal_uInt16 KEY_C
constexpr sal_uInt16 KEY_SUBTRACT
constexpr sal_uInt16 KEYGROUP_CURSOR
#define LINK(Instance, Class, Member)
#define SAL_WARN(area, stream)
css::uno::Sequence< DstElementType > containerToSequence(const SrcType &i_Container)
std::basic_string_view< charT, traits > getToken(std::basic_string_view< charT, traits > sv, charT delimiter, std::size_t &position)
css::uno::Reference< css::linguistic2::XProofreadingIterator > get(css::uno::Reference< css::uno::XComponentContext > const &context)
OUString toId(const void *pValue)
IMPL_LINK(CuiAboutConfigValueDialog, KeyInputHdl, const KeyEvent &, rKeyEvent, bool)
IMPL_LINK_NOARG(CuiAboutConfigTabPage, ResetBtnHdl_Impl, weld::Button &, void)
Prop_Impl(OUString sName, OUString sProperty, Any aValue)
TransliterationFlags transliterateFlags