Makefile.in | 3 RepositoryModule_host.mk | 3 bin/gbuild-to-ide | 2 comphelper/qa/string/test_string.cxx | 12 comphelper/source/misc/dispatchcommand.cxx | 2 comphelper/source/misc/string.cxx | 29 desktop/source/app/app.cxx | 1 include/comphelper/string.hxx | 3 include/sal/log-areas.dox | 2 include/sfx2/tabdlg.hxx | 3 include/svtools/treelistbox.hxx | 2 include/vcl/button.hxx | 23 include/vcl/combobox.hxx | 2 include/vcl/dialog.hxx | 2 include/vcl/dllapi.h | 6 include/vcl/edit.hxx | 2 include/vcl/lstbox.hxx | 2 include/vcl/spinfld.hxx | 2 include/vcl/tabctrl.hxx | 2 include/vcl/uitest/factory.hxx | 23 include/vcl/uitest/uiobject.hxx | 331 ++++++ include/vcl/uitest/uitest.hxx | 27 include/vcl/window.hxx | 13 offapi/UnoApi_offapi.mk | 7 offapi/com/sun/star/ui/test/UITest.idl | 29 offapi/com/sun/star/ui/test/XUIObject.idl | 34 offapi/com/sun/star/ui/test/XUITest.idl | 28 oox/source/export/chartexport.cxx | 20 sc/Library_sc.mk | 1 sc/source/ui/app/inputwin.cxx | 1 sc/source/ui/inc/gridwin.hxx | 3 sc/source/ui/inc/uiobject.hxx | 47 sc/source/ui/uitest/uiobject.cxx | 240 ++++ sc/source/ui/view/gridwin.cxx | 12 sd/Library_sd.mk | 1 sd/source/ui/framework/factories/BasicViewFactory.cxx | 7 sd/source/ui/inc/ViewShell.hxx | 2 sd/source/ui/inc/Window.hxx | 3 sd/source/ui/inc/uiobject.hxx | 52 sd/source/ui/slidesorter/shell/SlideSorterViewShell.cxx | 1 sd/source/ui/uitest/uiobject.cxx | 147 ++ sd/source/ui/view/sdwindow.cxx | 14 sd/source/ui/view/viewshel.cxx | 5 sfx2/Library_sfx.mk | 1 sfx2/inc/uitest/sfx_uiobject.hxx | 39 sfx2/source/dialog/tabdlg.cxx | 13 sfx2/source/uitest/sfx_uiobject.cxx | 90 + solenv/gbuild/Module.mk | 40 solenv/gbuild/Postprocess.mk | 1 solenv/gbuild/TargetLocations.mk | 3 solenv/gbuild/UITest.mk | 114 ++ solenv/gbuild/extensions/post_SpeedUpTargets.mk | 14 solenv/gbuild/gbuild.mk | 1 svtools/Library_svt.mk | 1 svtools/inc/uitest/uiobject.hxx | 28 svtools/source/contnr/treelistbox.cxx | 6 svtools/source/dialogs/wizardmachine.cxx | 3 svtools/source/uitest/uiobject.cxx | 36 sw/Library_sw.mk | 1 sw/source/uibase/docvw/edtwin.cxx | 1 sw/source/uibase/docvw/edtwin3.cxx | 6 sw/source/uibase/inc/edtwin.hxx | 2 sw/source/uibase/inc/uiobject.hxx | 42 sw/source/uibase/uitest/uiobject.cxx | 114 ++ uitest/Makefile | 14 uitest/Module_uitest.mk | 16 uitest/README | 1 uitest/UITest_calc_demo.mk | 15 uitest/UITest_writer_demo.mk | 15 uitest/calc_tests/about_test.py | 29 uitest/calc_tests/calc_demo.txt | 5 uitest/calc_tests/create_chart.py | 186 +++ uitest/calc_tests/create_range_name.py | 72 + uitest/calc_tests/function_wizard.py | 44 uitest/calc_tests/gridwindow.py | 65 + uitest/connection.py | 139 ++ uitest/demo_ui/checkbox.py | 42 uitest/demo_ui/combobox.py | 33 uitest/demo_ui/demo_ui.txt | 10 uitest/demo_ui/edit.py | 44 uitest/demo_ui/gridwin.py | 73 + uitest/demo_ui/listbox.py | 55 + uitest/demo_ui/radiobutton.py | 43 uitest/demo_ui/tabdialog.py | 54 + uitest/helper.py | 80 + uitest/impress_tests/start.py | 114 ++ uitest/main.py | 75 + uitest/uihelper/calc.py | 15 uitest/uitest_helper.py | 90 + uitest/writer_tests/start.py | 109 ++ uitest/writer_tests/writer_demo.txt | 4 vcl/CppunitTest_vcl_lifecycle.mk | 1 vcl/Library_vcl.mk | 5 vcl/inc/window.h | 1 vcl/source/control/button.cxx | 19 vcl/source/control/combobox.cxx | 6 vcl/source/control/edit.cxx | 6 vcl/source/control/listbox.cxx | 6 vcl/source/control/spinfld.cxx | 6 vcl/source/control/tabctrl.cxx | 12 vcl/source/uitest/uiobject.cxx | 863 ++++++++++++++++ vcl/source/uitest/uitest.cxx | 40 vcl/source/uitest/uno/uiobject_uno.cxx | 121 ++ vcl/source/uitest/uno/uiobject_uno.hxx | 67 + vcl/source/uitest/uno/uitest_uno.cxx | 108 ++ vcl/source/window/builder.cxx | 1 vcl/source/window/dialog.cxx | 25 vcl/source/window/layout.cxx | 7 vcl/source/window/window.cxx | 21 vcl/vcl.unx.component | 4 110 files changed, 4418 insertions(+), 50 deletions(-)
New commits: commit d534e939d4b9c8ac09cd1e7e28e5ad43d1ee56ec Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Thu May 26 12:48:06 2016 +0200 uitest: add the radiobutton demo Change-Id: I271a7388c2114304da26050f909c366edd8143b5 diff --git a/uitest/demo_ui/radiobutton.py b/uitest/demo_ui/radiobutton.py new file mode 100644 index 0000000..bd8b1db --- /dev/null +++ b/uitest/demo_ui/radiobutton.py @@ -0,0 +1,43 @@ +# -*- Mode: python; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +# +# This Source Code Form is subject to the terms of the Mozilla Public +# License, v. 2.0. If a copy of the MPL was not distributed with this +# file, You can obtain one at http://mozilla.org/MPL/2.0/. +# + +from uitest_helper import UITest + +from helper import mkPropertyValues + +import time + +try: + import pyuno + import uno + import unohelper +except ImportError: + print("pyuno not found: try to set PYTHONPATH and URE_BOOTSTRAP variables") + print("PYTHONPATH=/installation/opt/program") + print("URE_BOOTSTRAP=file:///installation/opt/program/fundamentalrc") + raise + +def toggle_radiobutton(xContext): + xUITest = xContext.ServiceManager.createInstanceWithContext( + "org.libreoffice.uitest.UITest", xContext) + + ui_test = UITest(xUITest, xContext) + + ui_test.create_doc_in_start_center("calc") + + ui_test.execute_dialog_through_command(".uno:FormatCellDialog") + xCellsDlg = xUITest.getTopFocusWindow() + xNegativeNumRedCB = xCellsDlg.getChild("negnumred") + xNegativeNumRedCB.executeAction("CLICK",tuple()) + + okBtn = xCellsDlg.getChild("ok") + okBtn.executeAction("CLICK", tuple()) + + ui_test.close_doc() + +# vim:set shiftwidth=4 softtabstop=4 expandtab: */ + commit ab74c7d4eae55d7301b0eabad8ec7f253028bc62 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat Jun 18 16:03:04 2016 +0200 uitest: loplugin:stringconstant Change-Id: I863615af7a942b91513511ba515b82f3523c6aa5 diff --git a/sd/source/ui/uitest/uiobject.cxx b/sd/source/ui/uitest/uiobject.cxx index a8c0227..03b1538 100644 --- a/sd/source/ui/uitest/uiobject.cxx +++ b/sd/source/ui/uitest/uiobject.cxx @@ -76,7 +76,7 @@ namespace { OUString getObjectName(SdrObject* pObject) { if (pObject->GetName().isEmpty()) - return OUString("Unnamed Drawinglayer object ") + OUString::number(pObject->GetOrdNum()); + return "Unnamed Drawinglayer object " + OUString::number(pObject->GetOrdNum()); else return pObject->GetName(); } commit 53bdc87a596676d3c4a787615f30466e4efc3f7c Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat Jun 18 16:01:48 2016 +0200 uitest: loplugin:staticcall Change-Id: I0e8fd138689e73cd0b320d0898e0410baa2bcfa9 diff --git a/vcl/source/uitest/uno/uitest_uno.cxx b/vcl/source/uitest/uno/uitest_uno.cxx index 10b7f12..5270089 100644 --- a/vcl/source/uitest/uno/uitest_uno.cxx +++ b/vcl/source/uitest/uno/uitest_uno.cxx @@ -69,13 +69,13 @@ void SAL_CALL UITestUnoObj::executeCommand(const OUString& rCommand) throw (css::uno::RuntimeException, std::exception) { SolarMutexGuard aGuard; - mpUITest->executeCommand(rCommand); + UITest::executeCommand(rCommand); } css::uno::Reference<css::ui::test::XUIObject> SAL_CALL UITestUnoObj::getTopFocusWindow() throw (css::uno::RuntimeException, std::exception) { - std::unique_ptr<UIObject> pObj = mpUITest->getFocusTopWindow(); + std::unique_ptr<UIObject> pObj = UITest::getFocusTopWindow(); return new UIObjectUnoObj(std::move(pObj)); } commit e6a92c923769f0f3351fa081b17cb132536f934c Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat Jun 18 16:00:38 2016 +0200 loplugin:unusedvariablecheck Change-Id: I8bd6447915942c1869ec186d8ca01e5ac43b3e8a diff --git a/desktop/source/app/app.cxx b/desktop/source/app/app.cxx index e4845d4..cee0fb9 100644 --- a/desktop/source/app/app.cxx +++ b/desktop/source/app/app.cxx @@ -1027,7 +1027,6 @@ bool crashReportInfoExists() if (sep >= 0) { std::string key = line.substr(0, sep); - std::string value = line.substr(sep + 1); if (key == "DumpFile") return true; } commit 89f3205a4aa0c3834a5099ff639d9474e996d93b Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat Jun 18 15:59:50 2016 +0200 uitest: loplugin:sallogareas Change-Id: Ieb01166fbb0b07d1218072ae8bb953a36582361c diff --git a/include/sal/log-areas.dox b/include/sal/log-areas.dox index 3a28b7c..dd32631 100644 --- a/include/sal/log-areas.dox +++ b/include/sal/log-areas.dox @@ -135,6 +135,7 @@ certain functionality. @li @c sc.orcus.table @li @c sc.qa @li @c sc.ui - Calc UI +@li @c sc.uitest - Calc UI Test part @li @c sc.viewdata @section desktop commit 97aa073301a85c82dff4de2d57268f47192d099d Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat Jun 18 15:58:52 2016 +0200 uitest: loplugin:stringconstant Change-Id: Ib63a978bd488f41602d982789699ba3f3ca2dcf0 diff --git a/sc/source/ui/uitest/uiobject.cxx b/sc/source/ui/uitest/uiobject.cxx index f46ce5b..298acf0 100644 --- a/sc/source/ui/uitest/uiobject.cxx +++ b/sc/source/ui/uitest/uiobject.cxx @@ -91,7 +91,7 @@ void ScGridWinUIObject::execute(const OUString& rAction, if (rParameters.find("EXTEND") != rParameters.end()) { auto itr = rParameters.find("EXTEND"); - if (itr->second.equalsIgnoreAsciiCaseAscii("true") || itr->second == "1") + if (itr->second.equalsIgnoreAsciiCase("true") || itr->second == "1") bExtend = true; } commit 27e08d44f47b1830776f1efbdcd5e0838914f684 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat Jun 18 15:57:34 2016 +0200 uitest: loplugin:implicitboolconversion Change-Id: Id852960cdfd49331251e89306a6a32eb9e45a666 diff --git a/sw/source/uibase/uitest/uiobject.cxx b/sw/source/uibase/uitest/uiobject.cxx index 9f4529d..8759705 100644 --- a/sw/source/uibase/uitest/uiobject.cxx +++ b/sw/source/uibase/uitest/uiobject.cxx @@ -44,14 +44,14 @@ StringMap SwEditWinUIObject::get_state() sal_uInt16 nPages = rWrtShell.GetPageCnt(); aMap["Pages"] = OUString::number(nPages); - aMap["StartWord"] = OUString::number(rWrtShell.IsStartWord()); - aMap["EndWord"] = OUString::number(rWrtShell.IsEndWord()); - aMap["StartSentence"] = OUString::number(rWrtShell.IsStartSentence()); - aMap["EndSentence"] = OUString::number(rWrtShell.IsEndSentence()); - aMap["StartPara"] = OUString::number(rWrtShell.IsSttPara()); - aMap["EndPara"] = OUString::number(rWrtShell.IsEndPara()); - aMap["StartDoc"] = OUString::number(rWrtShell.IsStartOfDoc()); - aMap["EndDoc"] = OUString::number(rWrtShell.IsEndOfDoc()); + aMap["StartWord"] = OUString::boolean(rWrtShell.IsStartWord()); + aMap["EndWord"] = OUString::boolean(rWrtShell.IsEndWord()); + aMap["StartSentence"] = OUString::boolean(rWrtShell.IsStartSentence()); + aMap["EndSentence"] = OUString::boolean(rWrtShell.IsEndSentence()); + aMap["StartPara"] = OUString::boolean(rWrtShell.IsSttPara()); + aMap["EndPara"] = OUString::boolean(rWrtShell.IsEndPara()); + aMap["StartDoc"] = OUString::boolean(rWrtShell.IsStartOfDoc()); + aMap["EndDoc"] = OUString::boolean(rWrtShell.IsEndOfDoc()); return aMap; } commit 55f93456744615174739364bb03676aa0f6986ce Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat Jun 18 14:06:08 2016 +0200 uitest: loplugin:staticmethods Change-Id: I741a41ea12fe0ee70a73e144d4601c8aafe30ac8 diff --git a/include/vcl/uitest/uitest.hxx b/include/vcl/uitest/uitest.hxx index 38966a0..9f226b8 100644 --- a/include/vcl/uitest/uitest.hxx +++ b/include/vcl/uitest/uitest.hxx @@ -19,9 +19,9 @@ class UITEST_DLLPUBLIC UITest { public: - void executeCommand(const OUString& rCommand); + static void executeCommand(const OUString& rCommand); - std::unique_ptr<UIObject> getFocusTopWindow(); + static std::unique_ptr<UIObject> getFocusTopWindow(); }; /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit 5abf40cb3cb37311ef658c799e17aabb8d54fb9e Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat Jun 18 14:05:43 2016 +0200 uitest: plugin:sallogareas Change-Id: Ib0ebd774542129f8a7c68e276f1f03cc46f32fb8 diff --git a/include/sal/log-areas.dox b/include/sal/log-areas.dox index 25588df..3a28b7c 100644 --- a/include/sal/log-areas.dox +++ b/include/sal/log-areas.dox @@ -446,6 +446,7 @@ certain functionality. @li @c vcl.screensaverinhibitor @li @c vcl.scrollbar - Scroll Bars @li @c vcl.sm - Session Manager +@li @c vcl.uitest - The UI testing framework code @li @c vcl.unity @li @c vcl.unx.print @li @c vcl.unx.dtrans commit 5c82caaab4cf63c9cda20791f77acae6649f518b Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat Jun 18 14:03:46 2016 +0200 uitest: loplugin:override Change-Id: I014e036c803ef7eeba265eb36782781c3a62672c diff --git a/include/vcl/dialog.hxx b/include/vcl/dialog.hxx index afa8c2e..ecf086d8 100644 --- a/include/vcl/dialog.hxx +++ b/include/vcl/dialog.hxx @@ -96,7 +96,7 @@ public: virtual short Execute(); bool IsInExecute() const { return mbInExecute; } - virtual FactoryFunction GetUITestFactory() const; + virtual FactoryFunction GetUITestFactory() const override; // Dialog::Execute replacement API public: commit 275dfaaffb2494214607a1c3e02a3e7fdd850865 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Thu May 26 12:44:34 2016 +0200 uitest: make the calc keycode demo a bit easier to understand Change-Id: Ia24747994dc45b8c6636aee37a55d2ba4672993a diff --git a/uitest/calc_tests/gridwindow.py b/uitest/calc_tests/gridwindow.py index ae16e40..1f01ec9 100644 --- a/uitest/calc_tests/gridwindow.py +++ b/uitest/calc_tests/gridwindow.py @@ -55,10 +55,11 @@ def special_keys(xContext): selectProps = mkPropertyValues({"CELL": "C3"}) xGridWindow.executeAction("SELECT", selectProps) - # TODO: how to handle the enter typeProps = mkPropertyValues({"KEYCODE": "CTRL+DOWN"}) xGridWindow.executeAction("TYPE", typeProps) + time.sleep(2) + ui_test.close_doc() # vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit 017d7b9f5483cc9373ace5fd02f55987d7eabe2a Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Thu May 26 12:43:23 2016 +0200 uitest: add more impress tests Change-Id: I89bd0af49e530382f0201a108f8798f9a9d689e3 diff --git a/uitest/impress_tests/start.py b/uitest/impress_tests/start.py index 0c5ef2a..c817cfe 100644 --- a/uitest/impress_tests/start.py +++ b/uitest/impress_tests/start.py @@ -29,6 +29,86 @@ def start_impress(xContext): ui_test.create_doc_in_start_center("impress") + xImpressDoc = xUITest.getTopFocusWindow() + print(get_state_as_dict(xImpressDoc)) + print(xImpressDoc.getChildren()) + + xEditWin = xImpressDoc.getChild("impress_win") + xEditWin.executeAction("SET", mkPropertyValues({"ZOOM": "200"})) + + print(xEditWin.getChildren()) + + time.sleep(5) + + ui_test.close_doc() + +def select_page(xContext): + xUITest = xContext.ServiceManager.createInstanceWithContext( + "org.libreoffice.uitest.UITest", xContext) + + ui_test = UITest(xUITest, xContext) + + ui_test.create_doc_in_start_center("impress") + + xImpressDoc = xUITest.getTopFocusWindow() + print(get_state_as_dict(xImpressDoc)) + print(xImpressDoc.getChildren()) + + xEditWin = xImpressDoc.getChild("impress_win") + + time.sleep(10) + print(get_state_as_dict(xEditWin)) + + xEditWin.executeAction("GOTO", mkPropertyValues({"PAGE": "2"})) + + time.sleep(5) + + print(get_state_as_dict(xEditWin)) + + ui_test.close_doc() + +def select_text(xContext): + xUITest = xContext.ServiceManager.createInstanceWithContext( + "org.libreoffice.uitest.UITest", xContext) + + ui_test = UITest(xUITest, xContext) + + ui_test.create_doc_in_start_center("impress") + + xImpressDoc = xUITest.getTopFocusWindow() + print(get_state_as_dict(xImpressDoc)) + print(xImpressDoc.getChildren()) + + xEditWin = xImpressDoc.getChild("impress_win") + + time.sleep(10) + + print(get_state_as_dict(xEditWin)) + + ui_test.close_doc() + +def select_object(xContext): + xUITest = xContext.ServiceManager.createInstanceWithContext( + "org.libreoffice.uitest.UITest", xContext) + + ui_test = UITest(xUITest, xContext) + + ui_test.create_doc_in_start_center("impress") + + xImpressDoc = xUITest.getTopFocusWindow() + print(get_state_as_dict(xImpressDoc)) + print(xImpressDoc.getChildren()) + + xEditWin = xImpressDoc.getChild("impress_win") + + xEditWin.executeAction("SELECT", mkPropertyValues({"OBJECT":"Unnamed Drawinglayer object 1"})) + time.sleep(2) + xEditWin.executeAction("DESELECT", tuple()) + + time.sleep(4) + + print(get_state_as_dict(xEditWin)) + ui_test.close_doc() # vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit 60fdd56760269d1cca2cade50a0f7a5e2635f5ed Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Mon May 23 05:22:33 2016 +0200 uitest: support more impress operations Change-Id: I74ab526dabbee1f8c203274f187c065d9fb413fd diff --git a/sd/source/ui/inc/uiobject.hxx b/sd/source/ui/inc/uiobject.hxx index f8b7e57..8e3d479 100644 --- a/sd/source/ui/inc/uiobject.hxx +++ b/sd/source/ui/inc/uiobject.hxx @@ -16,6 +16,9 @@ class DrawViewShell; } +class SdrObject; +class SdrPageView; + class ImpressWindowUIObject : public WindowUIObject { public: @@ -27,6 +30,8 @@ public: virtual void execute(const OUString& rAction, const StringMap& rParameters) override; + virtual std::set<OUString> get_children() const override; + static std::unique_ptr<UIObject> create(vcl::Window* pWindow); protected: @@ -37,7 +42,11 @@ private: VclPtr<sd::Window> mxWindow; - sd::DrawViewShell* getViewShell(); + sd::DrawViewShell* getViewShell() const; + + SdrObject* getObject(const OUString& rName); + + SdrPageView* getPageView(); }; /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sd/source/ui/uitest/uiobject.cxx b/sd/source/ui/uitest/uiobject.cxx index 90535c6..a8c0227 100644 --- a/sd/source/ui/uitest/uiobject.cxx +++ b/sd/source/ui/uitest/uiobject.cxx @@ -11,6 +11,7 @@ #include "Window.hxx" #include "DrawViewShell.hxx" +#include "sdpage.hxx" ImpressWindowUIObject::ImpressWindowUIObject(VclPtr<sd::Window> xWindow): WindowUIObject(xWindow), @@ -51,7 +52,53 @@ void ImpressWindowUIObject::execute(const OUString& rAction, getViewShell()->SwitchPage(nVal); } } - WindowUIObject::execute(rAction, rParameters); + else if (rAction == "SELECT") + { + if (rParameters.find("OBJECT") != rParameters.end()) + { + auto itr = rParameters.find("OBJECT"); + OUString aName = itr->second; + SdrObject* pObj = getObject(aName); + SdrPageView* pPageView = getPageView(); + getViewShell()->GetView()->MarkObj(pObj, pPageView); + } + } + else if (rAction == "DESELECT") + { + getViewShell()->GetView()->UnMarkAll(); + } + else + WindowUIObject::execute(rAction, rParameters); +} + +namespace { + +OUString getObjectName(SdrObject* pObject) +{ + if (pObject->GetName().isEmpty()) + return OUString("Unnamed Drawinglayer object ") + OUString::number(pObject->GetOrdNum()); + else + return pObject->GetName(); +} + +} + +std::set<OUString> ImpressWindowUIObject::get_children() const +{ + SdrPage* pPage = getViewShell()->getCurrentPage(); + + std::set<OUString> aRet; + if (!pPage) + return aRet; + + size_t nObjs = pPage->GetObjCount(); + for (size_t i = 0; i < nObjs; ++i) + { + SdrObject* pObject = pPage->GetObj(i); + aRet.insert(getObjectName(pObject)); + } + + return aRet; } OUString ImpressWindowUIObject::get_name() const @@ -66,7 +113,7 @@ std::unique_ptr<UIObject> ImpressWindowUIObject::create(vcl::Window* pWindow) return std::unique_ptr<UIObject>(new ImpressWindowUIObject(pWin)); } -sd::DrawViewShell* ImpressWindowUIObject::getViewShell() +sd::DrawViewShell* ImpressWindowUIObject::getViewShell() const { sd::DrawViewShell* pViewShell = dynamic_cast<sd::DrawViewShell*>(mxWindow->GetViewShell()); assert(pViewShell); @@ -74,4 +121,27 @@ sd::DrawViewShell* ImpressWindowUIObject::getViewShell() return pViewShell; } +SdrObject* ImpressWindowUIObject::getObject(const OUString& rName) +{ + SdrPage* pPage = getViewShell()->getCurrentPage(); + + if (!pPage) + return nullptr; + + size_t nObjs = pPage->GetObjCount(); + for (size_t i = 0; i < nObjs; ++i) + { + SdrObject* pObj = pPage->GetObj(i); + if (rName == getObjectName(pObj)) + return pObj; + } + + return nullptr; +} + +SdrPageView* ImpressWindowUIObject::getPageView() +{ + return getViewShell()->GetView()->GetSdrPageView(); +} + /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit fdfc55da301435dfd52b0365b8edda7aa893f983 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sun May 22 05:54:11 2016 +0200 uitest: add initial code for impress main edit window Change-Id: I82eabe1df33878316907e664ddbcd8edf6a73d33 diff --git a/sd/Library_sd.mk b/sd/Library_sd.mk index 76e35ae..ae04336 100644 --- a/sd/Library_sd.mk +++ b/sd/Library_sd.mk @@ -411,6 +411,7 @@ $(eval $(call gb_Library_add_exception_objects,sd,\ sd/source/ui/tools/SdGlobalResourceContainer \ sd/source/ui/tools/SlotStateListener \ sd/source/ui/tools/TimerBasedTaskExecution \ + sd/source/ui/uitest/uiobject \ sd/source/ui/unoidl/DrawController \ sd/source/ui/unoidl/SdUnoDrawView \ sd/source/ui/unoidl/SdUnoOutlineView \ diff --git a/sd/source/ui/inc/Window.hxx b/sd/source/ui/inc/Window.hxx index 6d9d869..bfd38f4 100644 --- a/sd/source/ui/inc/Window.hxx +++ b/sd/source/ui/inc/Window.hxx @@ -49,6 +49,7 @@ public: virtual void dispose() override; void SetViewShell (ViewShell* pViewSh); + ViewShell* GetViewShell(); /** Set the zoom factor to the specified value and center the display area around the zoom center. @@ -192,6 +193,8 @@ protected: Selection GetSurroundingTextSelection() const override; /// @see OutputDevice::LogicInvalidate(). void LogicInvalidate(const Rectangle* pRectangle) override; + + FactoryFunction GetUITestFactory() const override; }; } // end of namespace sd diff --git a/sd/source/ui/inc/uiobject.hxx b/sd/source/ui/inc/uiobject.hxx new file mode 100644 index 0000000..f8b7e57 --- /dev/null +++ b/sd/source/ui/inc/uiobject.hxx @@ -0,0 +1,43 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + */ + +#include <vcl/uitest/uiobject.hxx> + +namespace sd { + +class Window; +class DrawViewShell; + +} + +class ImpressWindowUIObject : public WindowUIObject +{ +public: + + ImpressWindowUIObject(VclPtr<sd::Window> xWindow); + + virtual StringMap get_state() override; + + virtual void execute(const OUString& rAction, + const StringMap& rParameters) override; + + static std::unique_ptr<UIObject> create(vcl::Window* pWindow); + +protected: + + virtual OUString get_name() const override; + +private: + + VclPtr<sd::Window> mxWindow; + + sd::DrawViewShell* getViewShell(); +}; + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sd/source/ui/uitest/uiobject.cxx b/sd/source/ui/uitest/uiobject.cxx new file mode 100644 index 0000000..90535c6 --- /dev/null +++ b/sd/source/ui/uitest/uiobject.cxx @@ -0,0 +1,77 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + */ + +#include "uiobject.hxx" + +#include "Window.hxx" +#include "DrawViewShell.hxx" + +ImpressWindowUIObject::ImpressWindowUIObject(VclPtr<sd::Window> xWindow): + WindowUIObject(xWindow), + mxWindow(xWindow) +{ +} + +StringMap ImpressWindowUIObject::get_state() +{ + StringMap aMap = WindowUIObject::get_state(); + + aMap["SelectedText"] = getViewShell()->GetSelectionText(); + aMap["CurrentSlide"] = OUString::number(getViewShell()->GetCurPageId()); + + return aMap; +} + +void ImpressWindowUIObject::execute(const OUString& rAction, + const StringMap& rParameters) +{ + if (rAction == "SET") + { + if (rParameters.find("ZOOM") != rParameters.end()) + { + auto itr = rParameters.find("ZOOM"); + OUString aVal = itr->second; + sal_Int32 nVal = aVal.toInt32(); + getViewShell()->SetZoom(nVal); + } + } + else if (rAction == "GOTO") + { + if (rParameters.find("PAGE") != rParameters.end()) + { + auto itr = rParameters.find("PAGE"); + OUString aVal = itr->second; + sal_Int32 nVal = aVal.toInt32(); + getViewShell()->SwitchPage(nVal); + } + } + WindowUIObject::execute(rAction, rParameters); +} + +OUString ImpressWindowUIObject::get_name() const +{ + return OUString("ImpressWindowUIObject"); +} + +std::unique_ptr<UIObject> ImpressWindowUIObject::create(vcl::Window* pWindow) +{ + sd::Window* pWin = dynamic_cast<sd::Window*>(pWindow); + assert(pWin); + return std::unique_ptr<UIObject>(new ImpressWindowUIObject(pWin)); +} + +sd::DrawViewShell* ImpressWindowUIObject::getViewShell() +{ + sd::DrawViewShell* pViewShell = dynamic_cast<sd::DrawViewShell*>(mxWindow->GetViewShell()); + assert(pViewShell); + + return pViewShell; +} + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sd/source/ui/view/sdwindow.cxx b/sd/source/ui/view/sdwindow.cxx index 580e7a6..f400e78 100644 --- a/sd/source/ui/view/sdwindow.cxx +++ b/sd/source/ui/view/sdwindow.cxx @@ -38,6 +38,7 @@ #include "AccessibleDrawDocumentView.hxx" #include "WindowUpdater.hxx" #include "ViewShellBase.hxx" +#include "uiobject.hxx" #include <vcl/svapp.hxx> #include <vcl/settings.hxx> @@ -129,6 +130,11 @@ void Window::SetViewShell (ViewShell* pViewSh) } } +ViewShell* Window::GetViewShell() +{ + return mpViewShell; +} + void Window::CalcMinZoom() { // Are we entitled to change the minimal zoom factor? @@ -1021,6 +1027,14 @@ void Window::LogicInvalidate(const Rectangle* pRectangle) rSfxViewShell.libreOfficeKitViewCallback(LOK_CALLBACK_INVALIDATE_TILES, sRectangle.getStr()); } +FactoryFunction Window::GetUITestFactory() const +{ + if (get_id() == "impress_win") + return ImpressWindowUIObject::create; + + return WindowUIObject::create; +} + } // end of namespace sd /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit b67527fb75cd95201d9251064e8b9d5b1c4fe62a Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sun May 22 05:52:36 2016 +0200 uitest: dump the implementation name as well Change-Id: Ifefc5eb8c271aae0c815bb68535b1e3eb8afb2cd diff --git a/vcl/source/uitest/uiobject.cxx b/vcl/source/uitest/uiobject.cxx index 512d053..0f399f1 100644 --- a/vcl/source/uitest/uiobject.cxx +++ b/vcl/source/uitest/uiobject.cxx @@ -392,6 +392,7 @@ OUString WindowUIObject::get_name() const void WindowUIObject::dumpState() const { DUMP_UITEST(get_name() << " " << mxWindow->get_id()); + DUMP_UITEST("Implementation Name: " << typeid(*mxWindow.get()).name()); StringMap aState = const_cast<WindowUIObject*>(this)->get_state(); for (auto itr = aState.begin(), itrEnd = aState.end(); itr != itrEnd; ++itr) { commit a32eb53ca1a379277b80a1ba01072a441f090919 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sun May 22 03:03:07 2016 +0200 uitest: annotate a few draw/impress windows Change-Id: I6352842535fddc99d30a4d0180ac01e7f8d5cd48 diff --git a/sd/source/ui/framework/factories/BasicViewFactory.cxx b/sd/source/ui/framework/factories/BasicViewFactory.cxx index 3c8cc02..de3d4d5 100644 --- a/sd/source/ui/framework/factories/BasicViewFactory.cxx +++ b/sd/source/ui/framework/factories/BasicViewFactory.cxx @@ -36,6 +36,7 @@ #include "SlideSorterViewShell.hxx" #include "FrameView.hxx" #include "facreg.hxx" +#include "Window.hxx" #include <sfx2/viewfrm.hxx> #include <vcl/wrkwin.hxx> @@ -341,6 +342,7 @@ std::shared_ptr<ViewShell> BasicViewFactory::CreateViewShell ( &rWindow, PK_STANDARD, pFrameView)); + pViewShell->GetContentWindow()->set_id("impress_win"); } else if (rsViewURL.equals(FrameworkHelper::msDrawViewURL)) { @@ -350,6 +352,7 @@ std::shared_ptr<ViewShell> BasicViewFactory::CreateViewShell ( *mpBase, &rWindow, pFrameView)); + pViewShell->GetContentWindow()->set_id("draw_win"); } else if (rsViewURL.equals(FrameworkHelper::msOutlineViewURL)) { @@ -359,6 +362,7 @@ std::shared_ptr<ViewShell> BasicViewFactory::CreateViewShell ( *mpBase, &rWindow, pFrameView)); + pViewShell->GetContentWindow()->set_id("outline_win"); } else if (rsViewURL.equals(FrameworkHelper::msNotesViewURL)) { @@ -369,6 +373,7 @@ std::shared_ptr<ViewShell> BasicViewFactory::CreateViewShell ( &rWindow, PK_NOTES, pFrameView)); + pViewShell->GetContentWindow()->set_id("notes_win"); } else if (rsViewURL.equals(FrameworkHelper::msHandoutViewURL)) { @@ -379,6 +384,7 @@ std::shared_ptr<ViewShell> BasicViewFactory::CreateViewShell ( &rWindow, PK_HANDOUT, pFrameView)); + pViewShell->GetContentWindow()->set_id("handout_win"); } else if (rsViewURL.equals(FrameworkHelper::msPresentationViewURL)) { @@ -388,6 +394,7 @@ std::shared_ptr<ViewShell> BasicViewFactory::CreateViewShell ( *mpBase, &rWindow, pFrameView)); + pViewShell->GetContentWindow()->set_id("presentation_win"); } else if (rsViewURL.equals(FrameworkHelper::msSlideSorterURL)) { diff --git a/sd/source/ui/inc/ViewShell.hxx b/sd/source/ui/inc/ViewShell.hxx index 462bfc5..4dd4fd9 100644 --- a/sd/source/ui/inc/ViewShell.hxx +++ b/sd/source/ui/inc/ViewShell.hxx @@ -142,6 +142,8 @@ public: */ inline vcl::Window* GetParentWindow() const { return mpParentWindow; } + sd::Window* GetContentWindow() const; + inline ::sd::View* GetView() const { return mpView; } inline SdrView* GetDrawView() const; SD_DLLPUBLIC DrawDocShell* GetDocSh() const; diff --git a/sd/source/ui/slidesorter/shell/SlideSorterViewShell.cxx b/sd/source/ui/slidesorter/shell/SlideSorterViewShell.cxx index 0b7ce99..ac9a8fc 100644 --- a/sd/source/ui/slidesorter/shell/SlideSorterViewShell.cxx +++ b/sd/source/ui/slidesorter/shell/SlideSorterViewShell.cxx @@ -123,6 +123,7 @@ SlideSorterViewShell::SlideSorterViewShell ( mpSlideSorter(), mbIsArrangeGUIElementsPending(true) { + GetContentWindow()->set_id("slidesorter"); meShellType = ST_SLIDE_SORTER; if (pFrameViewArgument != nullptr) diff --git a/sd/source/ui/view/viewshel.cxx b/sd/source/ui/view/viewshel.cxx index 942f9a5..84d5d19 100644 --- a/sd/source/ui/view/viewshel.cxx +++ b/sd/source/ui/view/viewshel.cxx @@ -1604,6 +1604,11 @@ void ViewShell::NotifyAccUpdate( ) GetViewShellBase().GetDrawController().NotifyAccUpdate(); } +sd::Window* ViewShell::GetContentWindow() const +{ + return mpContentWindow.get(); +} + } // end of namespace sd //===== ViewShellObjectBarFactory ============================================= commit a259b9935990ec7c1fd804c0ff9f0a8b6e9044ec Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sun May 22 01:43:16 2016 +0200 uitest: start with work on impress demos Change-Id: I8407fe37f8906e21abc1033d6adf44f31cad1572 diff --git a/uitest/impress_tests/start.py b/uitest/impress_tests/start.py new file mode 100644 index 0000000..0c5ef2a --- /dev/null +++ b/uitest/impress_tests/start.py @@ -0,0 +1,34 @@ +# -*- Mode: python; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +# +# This Source Code Form is subject to the terms of the Mozilla Public +# License, v. 2.0. If a copy of the MPL was not distributed with this +# file, You can obtain one at http://mozilla.org/MPL/2.0/. +# + +from uitest_helper import UITest, get_state_as_dict + +from helper import mkPropertyValues + +import time + +try: + import pyuno + import uno + import unohelper +except ImportError: + print("pyuno not found: try to set PYTHONPATH and URE_BOOTSTRAP variables") + print("PYTHONPATH=/installation/opt/program") + print("URE_BOOTSTRAP=file:///installation/opt/program/fundamentalrc") + raise + +def start_impress(xContext): + xUITest = xContext.ServiceManager.createInstanceWithContext( + "org.libreoffice.uitest.UITest", xContext) + + ui_test = UITest(xUITest, xContext) + + ui_test.create_doc_in_start_center("impress") + + ui_test.close_doc() + +# vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit 313265c26df651d57d59fa4527baf6752f6b2f2d Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sun May 22 01:39:09 2016 +0200 uitest: add writer demo ui tests to makefile Change-Id: I4ba2321deb196f22c95db533266d82c541a95f0a diff --git a/uitest/Module_uitest.mk b/uitest/Module_uitest.mk index 9ebc2f7..2530bee 100644 --- a/uitest/Module_uitest.mk +++ b/uitest/Module_uitest.mk @@ -12,5 +12,5 @@ $(eval $(call gb_Module_Module,uitest)) $(eval $(call gb_Module_add_uicheck_targets,uitest,\ UITest_calc_demo \ - UITest_demo_ui \ + UITest_writer_demo \ )) diff --git a/uitest/UITest_writer_demo.mk b/uitest/UITest_writer_demo.mk new file mode 100644 index 0000000..c0c7f3d --- /dev/null +++ b/uitest/UITest_writer_demo.mk @@ -0,0 +1,15 @@ +# -*- Mode: makefile-gmake; tab-width: 4; indent-tabs-mode: t -*- +# +# This file is part of the LibreOffice project. +# +# This Source Code Form is subject to the terms of the Mozilla Public +# License, v. 2.0. If a copy of the MPL was not distributed with this +# file, You can obtain one at http://mozilla.org/MPL/2.0/. +# + +$(eval $(call gb_UITest_UITest,writer_demo)) + +$(eval $(call gb_UITest_add_modules,writer_demo,$(SRCDIR)/uitest,\ + writer_tests/writer_demo.txt \ +)) +# vim: set noet sw=4 ts=4: diff --git a/uitest/writer_tests/writer_demo.txt b/uitest/writer_tests/writer_demo.txt new file mode 100644 index 0000000..0045e2a --- /dev/null +++ b/uitest/writer_tests/writer_demo.txt @@ -0,0 +1,4 @@ +writer_tests.start.start_writer +writer_tests.start.type_text +writer_tests.start.goto_first_page +writer_tests.start.select_text commit 83b0ec6201172190bdcb16753c1166264f5f6cc5 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat May 21 01:50:46 2016 +0200 uitest: add demo for selecting writer text Change-Id: Iffc3e16bf0fa5a02058b6ad008ff3f61ea2a23af diff --git a/uitest/writer_tests/start.py b/uitest/writer_tests/start.py index a0fe7d2..a5a23ca 100644 --- a/uitest/writer_tests/start.py +++ b/uitest/writer_tests/start.py @@ -81,4 +81,29 @@ def goto_first_page(xContext): ui_test.close_doc() + +def select_text(xContext): + xUITest = xContext.ServiceManager.createInstanceWithContext( + "org.libreoffice.uitest.UITest", xContext) + + ui_test = UITest(xUITest, xContext) + + ui_test.create_doc_in_start_center("writer") + + xWriterDoc = xUITest.getTopFocusWindow() + xWriterEdit = xWriterDoc.getChild("writer_edit") + + xWriterEdit.executeAction("TYPE", mkPropertyValues({"TEXT": "This is my first writer text written through the UI testing"})) + + time.sleep(2) + print(get_state_as_dict(xWriterEdit)) + + xWriterEdit.executeAction("SELECT", mkPropertyValues({"START_POS": "0", "END_POS": "4"})) + + print(get_state_as_dict(xWriterEdit)) + + time.sleep(2) + + ui_test.close_doc() + # vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit c1317d040c93816021268426d593b3e2cae871fe Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat May 21 01:50:13 2016 +0200 uitest: the demo is supposed to show how to goto the page start Change-Id: I61d2a74b50be2ab8b5077344ecd41cfa0cba2e64 diff --git a/uitest/writer_tests/start.py b/uitest/writer_tests/start.py index a9b722a..a0fe7d2 100644 --- a/uitest/writer_tests/start.py +++ b/uitest/writer_tests/start.py @@ -75,6 +75,8 @@ def goto_first_page(xContext): xWriterEdit.executeAction("TYPE", mkPropertyValues({"KEYCODE": "RETURN"})) state = get_state_as_dict(xWriterEdit) + xWriterEdit.executeAction("GOTO", mkPropertyValues({"PAGE": "1"})) + print(state) time.sleep(2) ui_test.close_doc() commit 3ba10adaa853da547aa90d69b666ada4e683fe32 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat May 21 01:49:19 2016 +0200 uitest: support selecting writer text Change-Id: I6d1c4e5a05bdcb3299af86a9044d912239659fb9 diff --git a/sw/source/uibase/uitest/uiobject.cxx b/sw/source/uibase/uitest/uiobject.cxx index 0102c98..9f4529d 100644 --- a/sw/source/uibase/uitest/uiobject.cxx +++ b/sw/source/uibase/uitest/uiobject.cxx @@ -79,6 +79,22 @@ void SwEditWinUIObject::execute(const OUString& rAction, getWrtShell(mxEditWin).GotoPage(nVal, false); } } + else if (rAction == "SELECT") + { + if (rParameters.find("START_POS") != rParameters.end()) + { + auto itr = rParameters.find("START_POS"); + OUString aStartPos = itr->second; + sal_Int32 nStartPos = aStartPos.toInt32(); + + itr = rParameters.find("END_POS"); + assert(itr != rParameters.end()); + OUString aEndPos = itr->second; + sal_Int32 nEndPos = aEndPos.toInt32(); + + getWrtShell(mxEditWin).SelectText(nStartPos, nEndPos); + } + } else WindowUIObject::execute(rAction, rParameters); } commit d2dc8ded7008908e9290cff3db4d14682e7cbe71 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat May 21 01:48:44 2016 +0200 uitest: add more properties to writer state Change-Id: Iadf223b38d84c1a6fb9892642f39e63dd16c72c8 diff --git a/sw/source/uibase/uitest/uiobject.cxx b/sw/source/uibase/uitest/uiobject.cxx index c6df6e1..0102c98 100644 --- a/sw/source/uibase/uitest/uiobject.cxx +++ b/sw/source/uibase/uitest/uiobject.cxx @@ -35,11 +35,24 @@ StringMap SwEditWinUIObject::get_state() sal_uInt16 nPageNum = 0; sal_uInt16 nVirtPageNum = 0; - getWrtShell(mxEditWin).GetPageNum(nPageNum, nVirtPageNum); + SwWrtShell& rWrtShell = getWrtShell(mxEditWin); + rWrtShell.GetPageNum(nPageNum, nVirtPageNum); aMap["CurrentPage"] = OUString::number(nPageNum); - getWrtShell(mxEditWin).GetPageNum(nPageNum, nVirtPageNum, false); + rWrtShell.GetPageNum(nPageNum, nVirtPageNum, false); aMap["TopVisiblePage"] = OUString::number(nPageNum); + sal_uInt16 nPages = rWrtShell.GetPageCnt(); + aMap["Pages"] = OUString::number(nPages); + + aMap["StartWord"] = OUString::number(rWrtShell.IsStartWord()); + aMap["EndWord"] = OUString::number(rWrtShell.IsEndWord()); + aMap["StartSentence"] = OUString::number(rWrtShell.IsStartSentence()); + aMap["EndSentence"] = OUString::number(rWrtShell.IsEndSentence()); + aMap["StartPara"] = OUString::number(rWrtShell.IsSttPara()); + aMap["EndPara"] = OUString::number(rWrtShell.IsEndPara()); + aMap["StartDoc"] = OUString::number(rWrtShell.IsStartOfDoc()); + aMap["EndDoc"] = OUString::number(rWrtShell.IsEndOfDoc()); + return aMap; } commit 0a52f261c6969992bb0b7ed3d8618884e1f62272 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat May 21 01:24:01 2016 +0200 uitest: add demo showing how to use page number Change-Id: I718f4c6c8f01ceb556b9beadce5af88491c4efe0 diff --git a/uitest/writer_tests/start.py b/uitest/writer_tests/start.py index 83b5ad2..a9b722a 100644 --- a/uitest/writer_tests/start.py +++ b/uitest/writer_tests/start.py @@ -5,7 +5,7 @@ # file, You can obtain one at http://mozilla.org/MPL/2.0/. # -from uitest_helper import UITest +from uitest_helper import UITest, get_state_as_dict from helper import mkPropertyValues @@ -58,4 +58,25 @@ def type_text(xContext): ui_test.close_doc() +def goto_first_page(xContext): + xUITest = xContext.ServiceManager.createInstanceWithContext( + "org.libreoffice.uitest.UITest", xContext) + + ui_test = UITest(xUITest, xContext) + + ui_test.create_doc_in_start_center("writer") + + xWriterDoc = xUITest.getTopFocusWindow() + xWriterEdit = xWriterDoc.getChild("writer_edit") + + state = get_state_as_dict(xWriterEdit) + print(state) + while state["CurrentPage"] is "1": + xWriterEdit.executeAction("TYPE", mkPropertyValues({"KEYCODE": "RETURN"})) + state = get_state_as_dict(xWriterEdit) + + time.sleep(2) + + ui_test.close_doc() + # vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit b78bd71b8d607e3ff773da1f972fec68934d4840 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat May 21 01:22:36 2016 +0200 uitest: provide a way to jump at the beginning of page Note that page numbers in writer are 1-based Change-Id: I614ff08927b4cb92d3819b557ec6791199da69a4 diff --git a/sw/source/uibase/uitest/uiobject.cxx b/sw/source/uibase/uitest/uiobject.cxx index 555aef4..c6df6e1 100644 --- a/sw/source/uibase/uitest/uiobject.cxx +++ b/sw/source/uibase/uitest/uiobject.cxx @@ -56,6 +56,16 @@ void SwEditWinUIObject::execute(const OUString& rAction, mxEditWin->GetView().SetZoom(SvxZoomType::PERCENT, nVal); } } + else if (rAction == "GOTO") + { + if (rParameters.find("PAGE") != rParameters.end()) + { + auto itr = rParameters.find("PAGE"); + OUString aVal = itr->second; + sal_Int32 nVal = aVal.toInt32(); + getWrtShell(mxEditWin).GotoPage(nVal, false); + } + } else WindowUIObject::execute(rAction, rParameters); } commit 8b21af2d243bf033f9a9375f48be840e61300fce Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat May 21 01:22:01 2016 +0200 uitest: provide information about current page Change-Id: Ie0ef65a023e156f65370e11f024fa6349841841e diff --git a/sw/source/uibase/uitest/uiobject.cxx b/sw/source/uibase/uitest/uiobject.cxx index 907e7b9..555aef4 100644 --- a/sw/source/uibase/uitest/uiobject.cxx +++ b/sw/source/uibase/uitest/uiobject.cxx @@ -10,6 +10,7 @@ #include "uiobject.hxx" #include "edtwin.hxx" #include "view.hxx" +#include "wrtsh.hxx" SwEditWinUIObject::SwEditWinUIObject(VclPtr<SwEditWin> xEditWin): WindowUIObject(xEditWin), @@ -17,11 +18,28 @@ SwEditWinUIObject::SwEditWinUIObject(VclPtr<SwEditWin> xEditWin): { } +namespace { + +SwWrtShell& getWrtShell(VclPtr<SwEditWin> xEditWin) +{ + return xEditWin->GetView().GetWrtShell(); +} + +} + StringMap SwEditWinUIObject::get_state() { StringMap aMap = WindowUIObject::get_state(); - // aMap["SelectedText"] = mxEditWin + aMap["SelectedText"] = mxEditWin->GetView().GetSelectionText(); + + sal_uInt16 nPageNum = 0; + sal_uInt16 nVirtPageNum = 0; + getWrtShell(mxEditWin).GetPageNum(nPageNum, nVirtPageNum); + aMap["CurrentPage"] = OUString::number(nPageNum); + getWrtShell(mxEditWin).GetPageNum(nPageNum, nVirtPageNum, false); + aMap["TopVisiblePage"] = OUString::number(nPageNum); + return aMap; } commit 229ab4ba12c3bf4ff535c150a9d2ef4ba29cfd57 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat May 21 01:21:08 2016 +0200 uitest: make handling the state of an object easier Change-Id: I3dcb78752b62a42d3aa283910241fef813dc352b diff --git a/uitest/uitest_helper.py b/uitest/uitest_helper.py index cac4ea1..925010e 100644 --- a/uitest/uitest_helper.py +++ b/uitest/uitest_helper.py @@ -9,6 +9,8 @@ import time from helper import EventListener +from helper import convert_property_values_to_dict + class DialogNotExecutedException(Exception): def __init__(self, command): self.command = command @@ -82,4 +84,7 @@ class UITest(object): time_ += self.DEFAULT_SLEEP time.sleep(self.DEFAULT_SLEEP) +def get_state_as_dict(ui_object): + return convert_property_values_to_dict(ui_object.getState()) + # vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit cb024cd4e9749ef4ad5a1bc19570623883da1d3b Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Sat May 21 01:19:00 2016 +0200 uitest: add a way to convert property values to dicts Change-Id: I21afd1c9b88525e576745905ee1ce21746f2d50c diff --git a/uitest/helper.py b/uitest/helper.py index 2d771e1..fcb9618 100644 --- a/uitest/helper.py +++ b/uitest/helper.py @@ -68,4 +68,13 @@ def mkPropertyValues(vals): """ return tuple([mkPropertyValue(name, value) for (name, value) in vals.items()]) +def convert_property_values_to_dict(propMap): + ret = {} + for entry in propMap: + name = entry.Name + val = entry.Value + ret[name] = val + + return ret + # vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit 18bfce49b17d648914df7f51dca9c5b115053b11 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Fri May 20 20:58:47 2016 +0200 uitest: add demo showing how to type text into writer Change-Id: I32598d12c85ad36d5c5d9ab00c184bfb7e39a4bd diff --git a/uitest/writer_tests/start.py b/uitest/writer_tests/start.py index 65ca0ed..83b5ad2 100644 --- a/uitest/writer_tests/start.py +++ b/uitest/writer_tests/start.py @@ -41,4 +41,21 @@ def start_writer(xContext): ui_test.close_doc() +def type_text(xContext): + xUITest = xContext.ServiceManager.createInstanceWithContext( + "org.libreoffice.uitest.UITest", xContext) + + ui_test = UITest(xUITest, xContext) + + ui_test.create_doc_in_start_center("writer") + + xWriterDoc = xUITest.getTopFocusWindow() + xWriterEdit = xWriterDoc.getChild("writer_edit") + + xWriterEdit.executeAction("TYPE", mkPropertyValues({"TEXT": "This is my first writer text written through the UI testing"})) + + time.sleep(2) + + ui_test.close_doc() + # vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit d9f8f73926ebbf030233731ed7f6bde06eb80d09 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Fri May 20 20:57:44 2016 +0200 uitest: forward unhandled actions to the base class Change-Id: Iac08e77d9b0e80f2af93c8b229d083603f1d22d4 diff --git a/sw/source/uibase/uitest/uiobject.cxx b/sw/source/uibase/uitest/uiobject.cxx index 9d45be1..907e7b9 100644 --- a/sw/source/uibase/uitest/uiobject.cxx +++ b/sw/source/uibase/uitest/uiobject.cxx @@ -38,6 +38,8 @@ void SwEditWinUIObject::execute(const OUString& rAction, mxEditWin->GetView().SetZoom(SvxZoomType::PERCENT, nVal); } } + else + WindowUIObject::execute(rAction, rParameters); } OUString SwEditWinUIObject::get_name() const commit ebbb900ea24e7db9b3956e24a8c5ba0263e62f03 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Fri May 20 20:50:43 2016 +0200 uitest: add initial writer demos Change-Id: If0aaf07b061fde3d5efa0d604af002efc872f726 diff --git a/uitest/writer_tests/start.py b/uitest/writer_tests/start.py new file mode 100644 index 0000000..65ca0ed --- /dev/null +++ b/uitest/writer_tests/start.py @@ -0,0 +1,44 @@ +# -*- Mode: python; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +# +# This Source Code Form is subject to the terms of the Mozilla Public +# License, v. 2.0. If a copy of the MPL was not distributed with this +# file, You can obtain one at http://mozilla.org/MPL/2.0/. +# + +from uitest_helper import UITest + +from helper import mkPropertyValues + +import time + +try: + import pyuno + import uno + import unohelper +except ImportError: + print("pyuno not found: try to set PYTHONPATH and URE_BOOTSTRAP variables") + print("PYTHONPATH=/installation/opt/program") + print("URE_BOOTSTRAP=file:///installation/opt/program/fundamentalrc") + raise + +def start_writer(xContext): + xUITest = xContext.ServiceManager.createInstanceWithContext( + "org.libreoffice.uitest.UITest", xContext) + + ui_test = UITest(xUITest, xContext) + + ui_test.create_doc_in_start_center("writer") + + xWriterDoc = xUITest.getTopFocusWindow() + print(xWriterDoc.getChildren()) + + xWriterEdit = xWriterDoc.getChild("writer_edit") + print(xWriterEdit.getState()) + + xWriterEdit.executeAction("SET", mkPropertyValues({"ZOOM": "200"})) + + time.sleep(2) + + ui_test.close_doc() + +# vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit 4eae49218f449b4057d15633c5be2b3b0f9b88f9 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Fri May 20 20:49:40 2016 +0200 uitest: add wrapper for writer's main edit window Change-Id: Ibd6ffe85ca95cdc915f5c73b1b566de1d7413ee7 diff --git a/sw/Library_sw.mk b/sw/Library_sw.mk index 0555d16..ea8c362 100644 --- a/sw/Library_sw.mk +++ b/sw/Library_sw.mk @@ -691,6 +691,7 @@ $(eval $(call gb_Library_add_exception_objects,sw,\ sw/source/uibase/table/chartins \ sw/source/uibase/table/swtablerep \ sw/source/uibase/table/tablemgr \ + sw/source/uibase/uitest/uiobject \ sw/source/uibase/uiview/formatclipboard \ sw/source/uibase/uiview/pview \ sw/source/uibase/uiview/scroll \ diff --git a/sw/source/uibase/docvw/edtwin3.cxx b/sw/source/uibase/docvw/edtwin3.cxx index 745bbd4..52c56de 100644 --- a/sw/source/uibase/docvw/edtwin3.cxx +++ b/sw/source/uibase/docvw/edtwin3.cxx @@ -34,6 +34,7 @@ #include "pagedesc.hxx" #include <frmatr.hxx> #include <editeng/frmdiritem.hxx> +#include "uiobject.hxx" // Core-Notify void ScrollMDI( SwViewShell* pVwSh, const SwRect &rRect, @@ -165,4 +166,9 @@ void SwEditWin::DataChanged( const DataChangedEvent& rDCEvt ) pSh->UnlockPaint(); } +FactoryFunction SwEditWin::GetUITestFactory() const +{ + return SwEditWinUIObject::create; +} + /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sw/source/uibase/inc/edtwin.hxx b/sw/source/uibase/inc/edtwin.hxx index cc4d528..1b713de 100644 --- a/sw/source/uibase/inc/edtwin.hxx +++ b/sw/source/uibase/inc/edtwin.hxx @@ -307,6 +307,8 @@ public: void SetCursorTwipPosition(const Point& rPosition, bool bPoint, bool bClearMark); /// Allows starting or ending a graphic move or resize action. void SetGraphicTwipPosition(bool bStart, const Point& rPosition); + + virtual FactoryFunction GetUITestFactory() const override; }; #endif diff --git a/sw/source/uibase/inc/uiobject.hxx b/sw/source/uibase/inc/uiobject.hxx new file mode 100644 index 0000000..568aa6c --- /dev/null +++ b/sw/source/uibase/inc/uiobject.hxx @@ -0,0 +1,42 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + */ + +#ifndef SW_SOURCE_UIBASE_INC_UIOBJECT_HXX +#define SW_SOURCE_UIBASE_INC_UIOBJECT_HXX + +#include <vcl/uitest/uiobject.hxx> + +class SwEditWin; + +class SwEditWinUIObject : public WindowUIObject +{ +public: + + SwEditWinUIObject(VclPtr<SwEditWin> xEditWin); + + virtual StringMap get_state() override; + + virtual void execute(const OUString& rAction, + const StringMap& rParameters) override; + + static std::unique_ptr<UIObject> create(vcl::Window* pWindow); + +protected: + + virtual OUString get_name() const override; + +private: + + VclPtr<SwEditWin> mxEditWin; + +}; + +#endif + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sw/source/uibase/uitest/uiobject.cxx b/sw/source/uibase/uitest/uiobject.cxx new file mode 100644 index 0000000..9d45be1 --- /dev/null +++ b/sw/source/uibase/uitest/uiobject.cxx @@ -0,0 +1,55 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + */ + +#include "uiobject.hxx" +#include "edtwin.hxx" +#include "view.hxx" + +SwEditWinUIObject::SwEditWinUIObject(VclPtr<SwEditWin> xEditWin): + WindowUIObject(xEditWin), + mxEditWin(xEditWin) +{ +} + +StringMap SwEditWinUIObject::get_state() +{ + StringMap aMap = WindowUIObject::get_state(); + + // aMap["SelectedText"] = mxEditWin + return aMap; +} + +void SwEditWinUIObject::execute(const OUString& rAction, + const StringMap& rParameters) +{ + if (rAction == "SET") + { + if (rParameters.find("ZOOM") != rParameters.end()) + { + auto itr = rParameters.find("ZOOM"); + OUString aVal = itr->second; + sal_Int32 nVal = aVal.toInt32(); + mxEditWin->GetView().SetZoom(SvxZoomType::PERCENT, nVal); + } + } +} + +OUString SwEditWinUIObject::get_name() const +{ + return OUString("SwEditWinUIObject"); +} + +std::unique_ptr<UIObject> SwEditWinUIObject::create(vcl::Window* pWindow) +{ + SwEditWin* pEditWin = dynamic_cast<SwEditWin*>(pWindow); + assert(pEditWin); + return std::unique_ptr<UIObject>(new SwEditWinUIObject(pEditWin)); +} + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit 725815366eb5543b4465af60a1072f1738db9147 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Fri May 20 05:34:45 2016 +0200 uitest: set id for main writer edit window Change-Id: Ie039b9983dd2aa6ec2c79b35bfd87161a57438b5 diff --git a/sw/source/uibase/docvw/edtwin.cxx b/sw/source/uibase/docvw/edtwin.cxx index 5f8e026..b184da1 100644 --- a/sw/source/uibase/docvw/edtwin.cxx +++ b/sw/source/uibase/docvw/edtwin.cxx @@ -5089,6 +5089,7 @@ SwEditWin::SwEditWin(vcl::Window *pParent, SwView &rMyView): m_nKS_NUMINDENTINC_Count(0), m_pFrameControlsManager(new SwFrameControlsManager(this)) { + set_id("writer_edit"); SetHelpId(HID_EDIT_WIN); EnableChildTransparentMode(); SetDialogControlFlags( DialogControlFlags::Return | DialogControlFlags::WantFocus ); commit c1191005c01ae5f512d7841736dd6eb6f0dc8049 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Fri May 20 05:12:33 2016 +0200 uitest: use the new cell content enter function Change-Id: I75ff56a903226797284dff7f556bd425d40b4fd4 diff --git a/uitest/calc_tests/gridwindow.py b/uitest/calc_tests/gridwindow.py index b67275a..ae16e40 100644 --- a/uitest/calc_tests/gridwindow.py +++ b/uitest/calc_tests/gridwindow.py @@ -9,6 +9,8 @@ from uitest_helper import UITest from helper import mkPropertyValues +from uihelper.calc import enter_text_to_cell + import time try: @@ -32,6 +34,11 @@ def input(xContext): xGridWindow = xTopWindow.getChild("grid_window") + enter_text_to_cell(xGridWindow, "C3", "=A1") + enter_text_to_cell(xGridWindow, "A1", "2") + + time.sleep(2) + ui_test.close_doc() def special_keys(xContext): commit 7ffaaf37c1e052339c1148283a773ce7e520739f Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Fri May 20 05:11:39 2016 +0200 uitest: split the demo Change-Id: Iec2acce4e7777995d3e5a8e4bea5f069f579721d diff --git a/uitest/calc_tests/gridwindow.py b/uitest/calc_tests/gridwindow.py index 642da4b..b67275a 100644 --- a/uitest/calc_tests/gridwindow.py +++ b/uitest/calc_tests/gridwindow.py @@ -32,6 +32,19 @@ def input(xContext): xGridWindow = xTopWindow.getChild("grid_window") + ui_test.close_doc() + +def special_keys(xContext): + xUITest = xContext.ServiceManager.createInstanceWithContext( + "org.libreoffice.uitest.UITest", xContext) + + ui_test = UITest(xUITest, xContext) + + ui_test.create_doc_in_start_center("calc") + xTopWindow = xUITest.getTopFocusWindow() + + xGridWindow = xTopWindow.getChild("grid_window") + selectProps = mkPropertyValues({"CELL": "C3"}) xGridWindow.executeAction("SELECT", selectProps) commit 4d7ace84c8b80177a5c8dae6f7ca9d8291fd2e5d Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Fri May 20 05:07:33 2016 +0200 uitest: add a demo case for new keycodes Change-Id: Ieec7fcd9b942d99d0dc16794856af4b1eabebde8 diff --git a/uitest/calc_tests/gridwindow.py b/uitest/calc_tests/gridwindow.py index 55005b2..642da4b 100644 --- a/uitest/calc_tests/gridwindow.py +++ b/uitest/calc_tests/gridwindow.py @@ -36,7 +36,7 @@ def input(xContext): xGridWindow.executeAction("SELECT", selectProps) # TODO: how to handle the enter - typeProps = mkPropertyValues({"TEXT": "=2"}) + typeProps = mkPropertyValues({"KEYCODE": "CTRL+DOWN"}) xGridWindow.executeAction("TYPE", typeProps) ui_test.close_doc() commit 7af600b43c40aa0744a951f55f5d6b63fe168088 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Fri May 20 04:59:37 2016 +0200 uitest: add calc uitest helper functions Change-Id: I9201f697ede4d5f9a541eb06f20162ec5ad0542d diff --git a/uitest/uihelper/__init__.py b/uitest/uihelper/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/uitest/uihelper/calc.py b/uitest/uihelper/calc.py new file mode 100644 index 0000000..66e85e1 --- /dev/null +++ b/uitest/uihelper/calc.py @@ -0,0 +1,15 @@ +# -*- Mode: python; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +# +# This Source Code Form is subject to the terms of the Mozilla Public +# License, v. 2.0. If a copy of the MPL was not distributed with this +# file, You can obtain one at http://mozilla.org/MPL/2.0/. +# + +from helper import mkPropertyValues + +def enter_text_to_cell(gridwin, cell, text): + gridwin.executeAction("SELECT", mkPropertyValues({"CELL": cell})) + gridwin.executeAction("TYPE", mkPropertyValues({"TEXT": text})) + gridwin.executeAction("TYPE", mkPropertyValues({"KEYCODE": "RETURN"})) + +# vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit 51a2cdb4fbe376c519544b8e484e03eebe943f76 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Fri May 20 04:58:56 2016 +0200 uitest: support more special keycodes Change-Id: Ief5fde7c9840de0f7b0a34fec24837e3a8e5ae70 diff --git a/vcl/source/uitest/uiobject.cxx b/vcl/source/uitest/uiobject.cxx index b7b39ea..512d053 100644 --- a/vcl/source/uitest/uiobject.cxx +++ b/vcl/source/uitest/uiobject.cxx @@ -132,6 +132,22 @@ std::vector<KeyEvent> generate_key_events_from_keycode(const OUString& rStr) { std::vector<KeyEvent> aEvents; + std::map<OUString, sal_uInt16> aKeyMap = { + {"ESC", KEY_ESCAPE}, + {"DOWN", KEY_DOWN}, + {"UP", KEY_UP}, + {"LEFT", KEY_LEFT}, + {"RIGHT", KEY_RIGHT}, + {"DELETE", KEY_DELETE}, + {"INSERT", KEY_INSERT}, + {"BACKSPACE", KEY_BACKSPACE}, + {"RETURN", KEY_RETURN}, + {"HOME", KEY_HOME}, + {"END", KEY_END}, + {"PAGEUP", KEY_PAGEUP}, + {"PAGEDOWN", KEY_PAGEDOWN} + }; + // split string along '+' // then translate to keycodes bool bShift = false; @@ -159,12 +175,21 @@ std::vector<KeyEvent> generate_key_events_from_keycode(const OUString& rStr) aRemainingText = aToken; } - for (sal_Int32 i = 0; i < aRemainingText.getLength(); ++i) + if (aKeyMap.find(aRemainingText) != aKeyMap.end()) + { + sal_uInt16 nKey = aKeyMap[aRemainingText]; + vcl::KeyCode aCode(nKey, bShift, bMod1, bMod2, false); + aEvents.push_back(KeyEvent( 'a', aCode)); + } + else { - bool bShiftThroughKey = false; - sal_uInt16 nKey = get_key(aRemainingText[i], bShiftThroughKey); - vcl::KeyCode aCode(nKey, bShift || bShiftThroughKey, bMod1, bMod2, false); - aEvents.push_back(KeyEvent(aRemainingText[i], aCode)); + for (sal_Int32 i = 0; i < aRemainingText.getLength(); ++i) + { + bool bShiftThroughKey = false; + sal_uInt16 nKey = get_key(aRemainingText[i], bShiftThroughKey); + vcl::KeyCode aCode(nKey, bShift || bShiftThroughKey, bMod1, bMod2, false); + aEvents.push_back(KeyEvent(aRemainingText[i], aCode)); + } } return aEvents; commit 559f2e233108ed5e9da305ffbf945d6ed568f7eb Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Thu May 19 20:52:43 2016 +0200 uitest: add demo showing how to activate chart Change-Id: I40293ca1f786c08a51d01fde5e90b75af2e67f6b diff --git a/uitest/calc_tests/create_chart.py b/uitest/calc_tests/create_chart.py index 30f0aa7..1e72df7 100644 --- a/uitest/calc_tests/create_chart.py +++ b/uitest/calc_tests/create_chart.py @@ -150,4 +150,37 @@ def deselect_chart(xContext): ui_test.close_doc() +def activate_chart(xContext): + xUITest = xContext.ServiceManager.createInstanceWithContext( + "org.libreoffice.uitest.UITest", xContext) + + ui_test = UITest(xUITest, xContext) + + ui_test.create_doc_in_start_center("calc") + + fill_spreadsheet(xUITest) + + xCalcDoc = xUITest.getTopFocusWindow() + xGridWindow = xCalcDoc.getChild("grid_window") + + ui_test.execute_dialog_through_command(".uno:InsertObjectChart") + + xChartDlg = xUITest.getTopFocusWindow() + + xNextBtn = xChartDlg.getChild("finish") + xNextBtn.executeAction("CLICK", tuple()) + + xGridWindow.executeAction("DESELECT", mkPropertyValues({"OBJECT": ""})) + + time.sleep(2) + + xGridWindow.executeAction("SELECT", mkPropertyValues({"OBJECT": "Object 1"})) + xGridWindow.executeAction("ACTIVATE", tuple()) + + time.sleep(2) + + xGridWindow.executeAction("DESELECT", mkPropertyValues({"OBJECT": ""})) + + ui_test.close_doc() + # vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit fc0c5d6163e99d29498c9b8599d9bdf9a3e4ca6c Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Thu May 19 20:46:58 2016 +0200 uitest: add demo showing how to deselect an UI object Change-Id: Ie755dd93296de4031abe36833872c58032271d22 diff --git a/uitest/calc_tests/create_chart.py b/uitest/calc_tests/create_chart.py index 7bb331c..30f0aa7 100644 --- a/uitest/calc_tests/create_chart.py +++ b/uitest/calc_tests/create_chart.py @@ -124,4 +124,30 @@ def create_from_second_page(xContext): ui_test.close_doc() +def deselect_chart(xContext): + xUITest = xContext.ServiceManager.createInstanceWithContext( + "org.libreoffice.uitest.UITest", xContext) + + ui_test = UITest(xUITest, xContext) + + ui_test.create_doc_in_start_center("calc") + + fill_spreadsheet(xUITest) + + xCalcDoc = xUITest.getTopFocusWindow() + xGridWindow = xCalcDoc.getChild("grid_window") + + ui_test.execute_dialog_through_command(".uno:InsertObjectChart") + + xChartDlg = xUITest.getTopFocusWindow() + + xNextBtn = xChartDlg.getChild("finish") + xNextBtn.executeAction("CLICK", tuple()) + + xGridWindow.executeAction("DESELECT", mkPropertyValues({"OBJECT": ""})) + + time.sleep(2) + + ui_test.close_doc() + # vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit 20f74cf32bef511fd99f6d4689a5425a9145ebf1 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Thu May 19 20:46:26 2016 +0200 uitest: add way to deselect OLE object Change-Id: I34515de0b149147e40c23df6fef1339d0b69d469 diff --git a/sc/source/ui/uitest/uiobject.cxx b/sc/source/ui/uitest/uiobject.cxx index 4405fd9..f46ce5b 100644 --- a/sc/source/ui/uitest/uiobject.cxx +++ b/sc/source/ui/uitest/uiobject.cxx @@ -133,6 +133,17 @@ void ScGridWinUIObject::execute(const OUString& rAction, SAL_WARN("sc.uitest", "unknown selection method"); } } + else if (rAction == "DESELECT") + { + if (rParameters.find("OBJECT") != rParameters.end()) + { + ScDrawView* pDrawView = getDrawView(); + pDrawView->UnmarkAll(); + + ScTabViewShell* pViewShell = getViewShell(); + pViewShell->SetDrawShell(false); + } + } else if (rAction == "ACTIVATE") { ScDrawView* pDrawView = getDrawView(); commit 2d92504b2d8ff04b2fd8cea4fe4897cfbf82621f Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Thu May 19 20:21:06 2016 +0200 uitest: allow activating OLE objects Change-Id: I960f5d644afb9392f8b3fe1d2f393c499af57bdb diff --git a/sc/source/ui/inc/uiobject.hxx b/sc/source/ui/inc/uiobject.hxx index 85dee59..f5e6ba9 100644 --- a/sc/source/ui/inc/uiobject.hxx +++ b/sc/source/ui/inc/uiobject.hxx @@ -12,6 +12,7 @@ class ScGridWindow; class ScDBFunc; class ScDrawView; +class ScTabViewShell; class ScGridWinUIObject : public WindowUIObject { @@ -40,6 +41,7 @@ private: ScDBFunc* getDBFunc(); ScDrawView* getDrawView(); + ScTabViewShell* getViewShell(); }; /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sc/source/ui/uitest/uiobject.cxx b/sc/source/ui/uitest/uiobject.cxx index 84808c4..4405fd9 100644 --- a/sc/source/ui/uitest/uiobject.cxx +++ b/sc/source/ui/uitest/uiobject.cxx @@ -74,6 +74,14 @@ ScDrawView* ScGridWinUIObject::getDrawView() return pDrawView; } +ScTabViewShell* ScGridWinUIObject::getViewShell() +{ + ScViewData* pViewData = mxGridWindow->getViewData(); + ScTabViewShell* pViewShell = pViewData->GetViewShell(); + + return pViewShell; +} + void ScGridWinUIObject::execute(const OUString& rAction, const StringMap& rParameters) { @@ -125,6 +133,28 @@ void ScGridWinUIObject::execute(const OUString& rAction, SAL_WARN("sc.uitest", "unknown selection method"); } } + else if (rAction == "ACTIVATE") + { + ScDrawView* pDrawView = getDrawView(); + const SdrMarkList& rMarkList = pDrawView->GetMarkedObjectList(); + if (rMarkList.GetMarkCount() == 1) + { + SdrMark* pMark = rMarkList.GetMark(0); + SdrObject* pObj = pMark->GetMarkedSdrObj(); + sal_uInt16 nSdrObjKind = pObj->GetObjIdentifier(); + if (nSdrObjKind == OBJ_OLE2) + { + ScTabViewShell* pViewShell = getViewShell(); + pViewShell->ActivateObject( static_cast<SdrOle2Obj*>(pObj), 0 ); + } + else + { + SAL_WARN("sc.uitest", "can't activate non-ole objects"); + } + } + else + SAL_WARN("sc.uitest", "can't activate the current selection"); + } else { WindowUIObject::execute(rAction, rParameters); commit 54d5931880e141fb3eb963da7040035569cfd8f3 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Thu May 19 19:30:19 2016 +0200 uitest: allow to select charts in calc Change-Id: I7fd899d7abda968e9c849e46714208a650b3cfdb diff --git a/sc/source/ui/inc/uiobject.hxx b/sc/source/ui/inc/uiobject.hxx index 91d21a4..85dee59 100644 --- a/sc/source/ui/inc/uiobject.hxx +++ b/sc/source/ui/inc/uiobject.hxx @@ -11,6 +11,7 @@ class ScGridWindow; class ScDBFunc; +class ScDrawView; class ScGridWinUIObject : public WindowUIObject { @@ -38,6 +39,7 @@ protected: private: ScDBFunc* getDBFunc(); + ScDrawView* getDrawView(); }; /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sc/source/ui/uitest/uiobject.cxx b/sc/source/ui/uitest/uiobject.cxx index 550aeef..84808c4 100644 --- a/sc/source/ui/uitest/uiobject.cxx +++ b/sc/source/ui/uitest/uiobject.cxx @@ -14,6 +14,7 @@ #include "viewdata.hxx" #include "dbfunc.hxx" +#include "tabvwsh.hxx" #include <svx/svditer.hxx> #include <svx/svdobj.hxx> @@ -65,6 +66,14 @@ ScDBFunc* ScGridWinUIObject::getDBFunc() return pFunc; } +ScDrawView* ScGridWinUIObject::getDrawView() +{ + ScViewData* pViewData = mxGridWindow->getViewData(); + ScDrawView* pDrawView = pViewData->GetScDrawView(); + + return pDrawView; +} + void ScGridWinUIObject::execute(const OUString& rAction, const StringMap& rParameters) { @@ -103,6 +112,14 @@ void ScGridWinUIObject::execute(const OUString& rAction, sal_Int32 nTab = rStr.toUInt32(); mxGridWindow->getViewData()->SetTabNo(nTab); } + else if (rParameters.find("OBJECT") != rParameters.end()) + { + auto itr = rParameters.find("OBJECT"); + const OUString rStr = itr->second; + + ScDrawView* pDrawView = getDrawView(); + pDrawView->SelectObject(rStr); + } else { SAL_WARN("sc.uitest", "unknown selection method"); commit e0e414cd79c6faaa8a2770742b103b5df7efa487 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Thu May 19 19:28:58 2016 +0200 uitest: provide charts as children of calc's grid window diff --git a/sc/source/ui/inc/uiobject.hxx b/sc/source/ui/inc/uiobject.hxx index df14daf..91d21a4 100644 --- a/sc/source/ui/inc/uiobject.hxx +++ b/sc/source/ui/inc/uiobject.hxx @@ -29,6 +29,8 @@ public: static std::unique_ptr<UIObject> create(vcl::Window* pWindow); + virtual std::set<OUString> get_children() const override; + protected: virtual OUString get_name() const override; diff --git a/sc/source/ui/uitest/uiobject.cxx b/sc/source/ui/uitest/uiobject.cxx index d257b41..550aeef 100644 --- a/sc/source/ui/uitest/uiobject.cxx +++ b/sc/source/ui/uitest/uiobject.cxx @@ -15,6 +15,11 @@ #include "viewdata.hxx" #include "dbfunc.hxx" +#include <svx/svditer.hxx> +#include <svx/svdobj.hxx> +#include <svx/svdpage.hxx> +#include <svx/svdoole2.hxx> + namespace { ScAddress get_address_from_string(const OUString& rStr) @@ -109,6 +114,54 @@ void ScGridWinUIObject::execute(const OUString& rAction, } } +namespace { + +ScDrawLayer* get_draw_layer(VclPtr<ScGridWindow> xGridWindow) +{ + return xGridWindow->getViewData()->GetDocument()->GetDrawLayer(); +} + +SdrPage* get_draw_page(VclPtr<ScGridWindow> xGridWindow, SCTAB nTab) +{ + ScDrawLayer* pDrawLayer = get_draw_layer(xGridWindow); + + return pDrawLayer->GetPage(nTab); +} + +std::set<OUString> collect_charts(VclPtr<ScGridWindow> xGridWindow) +{ + SCTAB nTab = xGridWindow->getViewData()->GetTabNo(); + SdrPage* pPage = get_draw_page(xGridWindow, nTab); + + std::set<OUString> aRet; + + if (!pPage) + return aRet; + + SdrObjListIter aIter( *pPage, IM_FLAT ); + SdrObject* pObject = aIter.Next(); + while (pObject) + { + if (pObject->GetObjIdentifier() == OBJ_OLE2) + { + aRet.insert(static_cast<SdrOle2Obj*>(pObject)->GetPersistName()); + } + else + SAL_DEBUG(pObject->GetName()); + pObject = aIter.Next(); + } + + return aRet; +} + +} + +std::set<OUString> ScGridWinUIObject::get_children() const +{ + std::set<OUString> aChildren = collect_charts(mxGridWindow); + return aChildren; +} + std::unique_ptr<UIObject> ScGridWinUIObject::get_child(const OUString& /*rID*/) { return nullptr; commit 8a9861c47b66afed9f9a22ee7f507ba99cd4162a Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Thu May 19 03:36:42 2016 +0200 uitest: add demo for chart wizard Change-Id: I36b89e167408c2ab8b2a0f7d275ecb2dda4722b7 diff --git a/uitest/calc_tests/create_chart.py b/uitest/calc_tests/create_chart.py new file mode 100644 index 0000000..7bb331c --- /dev/null +++ b/uitest/calc_tests/create_chart.py @@ -0,0 +1,127 @@ +# -*- Mode: python; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +# +# This Source Code Form is subject to the terms of the Mozilla Public +# License, v. 2.0. If a copy of the MPL was not distributed with this +# file, You can obtain one at http://mozilla.org/MPL/2.0/. +# + +from uitest_helper import UITest + +from helper import mkPropertyValues + +import time + +try: + import pyuno + import uno + import unohelper +except ImportError: + print("pyuno not found: try to set PYTHONPATH and URE_BOOTSTRAP variables") + print("PYTHONPATH=/installation/opt/program") + print("URE_BOOTSTRAP=file:///installation/opt/program/fundamentalrc") + raise + +def add_content_to_cell(gridwin, cell, content): + selectProps = mkPropertyValues({"CELL": cell}) + gridwin.executeAction("SELECT", selectProps) + + contentProps = mkPropertyValues({"TEXT": content}) + gridwin.executeAction("TYPE", contentProps) + + +def fill_spreadsheet(xUITest): + xCalcDoc = xUITest.getTopFocusWindow() + xGridWindow = xCalcDoc.getChild("grid_window") + + add_content_to_cell(xGridWindow, "A1", "col1") + add_content_to_cell(xGridWindow, "B1", "col2") + add_content_to_cell(xGridWindow, "C1", "col3") + add_content_to_cell(xGridWindow, "A2", "1") + add_content_to_cell(xGridWindow, "B2", "3") + add_content_to_cell(xGridWindow, "C2", "5") + + xGridWindow.executeAction("SELECT", mkPropertyValues({"RANGE": "A1:C2"})) + +def cancel_immediately(xContext): + xUITest = xContext.ServiceManager.createInstanceWithContext( + "org.libreoffice.uitest.UITest", xContext) + + ui_test = UITest(xUITest, xContext) + + ui_test.create_doc_in_start_center("calc") + + fill_spreadsheet(xUITest) + + ui_test.execute_dialog_through_command(".uno:InsertObjectChart") + + xChartDlg = xUITest.getTopFocusWindow() + + xCancelBtn = xChartDlg.getChild("cancel") + xCancelBtn.executeAction("CLICK", tuple()) + + ui_test.close_doc() + +def create_from_first_page(xContext): + xUITest = xContext.ServiceManager.createInstanceWithContext( + "org.libreoffice.uitest.UITest", xContext) + + ui_test = UITest(xUITest, xContext) + + ui_test.create_doc_in_start_center("calc") + + fill_spreadsheet(xUITest) + + ui_test.execute_dialog_through_command(".uno:InsertObjectChart") + + xChartDlg = xUITest.getTopFocusWindow() + print(xChartDlg.getChildren()) + time.sleep(2) + + xOkBtn = xChartDlg.getChild("finish") + xOkBtn.executeAction("CLICK", tuple()) + + time.sleep(2) + + ui_test.close_doc() + +def create_from_second_page(xContext): + xUITest = xContext.ServiceManager.createInstanceWithContext( + "org.libreoffice.uitest.UITest", xContext) + + ui_test = UITest(xUITest, xContext) + + ui_test.create_doc_in_start_center("calc") + + fill_spreadsheet(xUITest) + + ui_test.execute_dialog_through_command(".uno:InsertObjectChart") + + xChartDlg = xUITest.getTopFocusWindow() + print(xChartDlg.getChildren()) + time.sleep(2) + + xNextBtn = xChartDlg.getChild("next") + xNextBtn.executeAction("CLICK", tuple()) + + print(xChartDlg.getChildren()) + + time.sleep(2) + + xDataInRows = xChartDlg.getChild("RB_DATAROWS") + xDataInRows.executeAction("CLICK", tuple()) + + time.sleep(2) + + xDataInCols = xChartDlg.getChild("RB_DATACOLS") + xDataInCols.executeAction("CLICK", tuple()) + + time.sleep(2) + + xCancelBtn = xChartDlg.getChild("finish") + xCancelBtn.executeAction("CLICK", tuple()) + + time.sleep(5) + + ui_test.close_doc() + +# vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit 99a934520777a5d3f6323e8f52f8dc388239cfe7 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Thu May 19 03:36:18 2016 +0200 uitest: add wrapper for radio button Change-Id: I8b4b35ac313796364502f8e9e2e836dc21f48a42 diff --git a/include/vcl/button.hxx b/include/vcl/button.hxx index e9c8df9..0fb7c98 100644 --- a/include/vcl/button.hxx +++ b/include/vcl/button.hxx @@ -388,6 +388,8 @@ public: */ void group(RadioButton &rOther); virtual void ShowFocus(const Rectangle& rRect) override; + + virtual FactoryFunction GetUITestFactory() const override; }; class VCL_DLLPUBLIC CheckBox : public Button diff --git a/include/vcl/uitest/uiobject.hxx b/include/vcl/uitest/uiobject.hxx index f00d80f..0baddeb 100644 --- a/include/vcl/uitest/uiobject.hxx +++ b/include/vcl/uitest/uiobject.hxx @@ -199,6 +199,27 @@ protected: virtual OUString get_name() const override; }; +class UITEST_DLLPUBLIC RadioButtonUIObject : public WindowUIObject +{ +private: + VclPtr<RadioButton> mxRadioButton; + +public: + RadioButtonUIObject(VclPtr<RadioButton> xCheckbox); + virtual ~RadioButtonUIObject(); + + virtual void execute(const OUString& rAction, + const StringMap& rParameters) override; + + virtual StringMap get_state() override; + + static std::unique_ptr<UIObject> create(vcl::Window* pWindow); + +protected: + + virtual OUString get_name() const override; +}; + class UITEST_DLLPUBLIC TabPageUIObject : public WindowUIObject { private: diff --git a/vcl/source/control/button.cxx b/vcl/source/control/button.cxx index 0546be2..ae8279c 100644 --- a/vcl/source/control/button.cxx +++ b/vcl/source/control/button.cxx @@ -2949,6 +2949,11 @@ void RadioButton::ShowFocus(const Rectangle& rRect) Button::ShowFocus(rRect); } +FactoryFunction RadioButton::GetUITestFactory() const +{ + return RadioButtonUIObject::create; +} + void CheckBox::ImplInitCheckBoxData() { meState = TRISTATE_FALSE; diff --git a/vcl/source/uitest/uiobject.cxx b/vcl/source/uitest/uiobject.cxx index 6b4c471..b7b39ea 100644 --- a/vcl/source/uitest/uiobject.cxx +++ b/vcl/source/uitest/uiobject.cxx @@ -581,6 +581,44 @@ std::unique_ptr<UIObject> CheckBoxUIObject::create(vcl::Window* pWindow) return std::unique_ptr<UIObject>(new CheckBoxUIObject(pCheckBox)); } +RadioButtonUIObject::RadioButtonUIObject(VclPtr<RadioButton> xRadioButton): + WindowUIObject(xRadioButton), + mxRadioButton(xRadioButton) +{ +} + +RadioButtonUIObject::~RadioButtonUIObject() +{ +} + +void RadioButtonUIObject::execute(const OUString& rAction, + const StringMap& /*rParameters*/) +{ + if (rAction == "CLICK") + { + mxRadioButton->ImplCallClick(); + } +} + +StringMap RadioButtonUIObject::get_state() +{ + StringMap aMap = WindowUIObject::get_state(); + + return aMap; +} + +OUString RadioButtonUIObject::get_name() const +{ + return OUString("RadioButtonUIObject"); +} + +std::unique_ptr<UIObject> RadioButtonUIObject::create(vcl::Window* pWindow) +{ + RadioButton* pRadioButton = dynamic_cast<RadioButton*>(pWindow); + assert(pRadioButton); + return std::unique_ptr<UIObject>(new RadioButtonUIObject(pRadioButton)); +} + TabPageUIObject::TabPageUIObject(VclPtr<TabPage> xTabPage): WindowUIObject(xTabPage), mxTabPage(xTabPage) commit cca08f80b37e05564cffd2f51afd54322848112c Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Thu May 19 03:35:08 2016 +0200 uitest: allow to disable tests Change-Id: I67afd5d537e8dd80549c1bf6de51fc92b127f836 diff --git a/uitest/main.py b/uitest/main.py index 9cda053..9039320 100644 --- a/uitest/main.py +++ b/uitest/main.py @@ -13,6 +13,9 @@ import importlib from connection import PersistentConnection, OfficeConnection def load_test(name): + if name.startswith("#"): + return None + module_name, obj_name = name.rsplit(".", 1) module = importlib.import_module(module_name) obj = getattr(module, obj_name) @@ -20,10 +23,13 @@ def load_test(name): def generic_test(opts, test_name): print("executing: " + test_name) + func = load_test(test_name) + if func is None: + return + connection = PersistentConnection(opts) connection.setUp() xContext = connection.getContext() - func = load_test(test_name) func(xContext) connection.tearDown() commit d3868095865f2336c5d04dbd5799990bb7b37e0e Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Thu May 19 02:20:31 2016 +0200 uitest: add missing override Change-Id: I5f3941550bd9256125d74f25e9e512b302e1e27d diff --git a/include/vcl/button.hxx b/include/vcl/button.hxx index 472949d..e9c8df9 100644 --- a/include/vcl/button.hxx +++ b/include/vcl/button.hxx @@ -96,7 +96,7 @@ public: /// Sets the button state according to the FeatureStateEvent emitted by an Uno state change. virtual void statusChanged(const css::frame::FeatureStateEvent& rEvent); - virtual FactoryFunction GetUITestFactory() const; + virtual FactoryFunction GetUITestFactory() const override; protected: commit 742a1d7ea13be85947e103a506844dea450da1cc Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Thu May 19 02:19:33 2016 +0200 uitest: set ids for a few UI objects created in code Change-Id: I421b97448bb596b134908ca6ddd60d7b4f60b186 diff --git a/sfx2/source/dialog/tabdlg.cxx b/sfx2/source/dialog/tabdlg.cxx index 4b33e31..84dcd1c 100644 --- a/sfx2/source/dialog/tabdlg.cxx +++ b/sfx2/source/dialog/tabdlg.cxx @@ -440,14 +440,20 @@ void SfxTabDialog::Init_Impl(bool bFmtFlag) m_pResetBtn = m_pUIBuilder->get<PushButton>("reset"); m_bOwnsResetBtn = m_pResetBtn == nullptr; if (m_bOwnsResetBtn) + { m_pResetBtn = VclPtr<PushButton>::Create(m_pActionArea.get()); + m_pResetBtn->set_id("reset"); + } else m_pImpl->bHideResetBtn = !m_pResetBtn->IsVisible(); m_pBaseFmtBtn = m_pUIBuilder->get<PushButton>("standard"); m_bOwnsBaseFmtBtn = m_pBaseFmtBtn == nullptr; if (m_bOwnsBaseFmtBtn) + { m_pBaseFmtBtn = VclPtr<PushButton>::Create(m_pActionArea.get()); + m_pBaseFmtBtn->set_id("standard"); + } m_pOKBtn->SetClickHdl( LINK( this, SfxTabDialog, OkHdl ) ); m_pCancelBtn->SetClickHdl( LINK( this, SfxTabDialog, CancelHdl ) ); diff --git a/svtools/source/dialogs/wizardmachine.cxx b/svtools/source/dialogs/wizardmachine.cxx index f7066e0..b83ca08 100644 --- a/svtools/source/dialogs/wizardmachine.cxx +++ b/svtools/source/dialogs/wizardmachine.cxx @@ -143,6 +143,7 @@ namespace svt m_pPrevPage->SetSizePixel( LogicToPixel( Size( 50, 14 ), MAP_APPFONT ) ); m_pPrevPage->SetText(SVT_RESSTR(STR_WIZDLG_PREVIOUS)); m_pPrevPage->Show(); + m_pPrevPage->set_id("previous"); if (_nButtonFlags & WizardButtonFlags::NEXT) AddButton( m_pPrevPage, ( WIZARDDIALOG_BUTTON_SMALLSTDOFFSET_X) ); // half x-offset to the next button @@ -160,6 +161,7 @@ namespace svt m_pNextPage->SetSizePixel( LogicToPixel( Size( 50, 14 ), MAP_APPFONT ) ); m_pNextPage->SetText(OUString(SVT_RESSTR(STR_WIZDLG_NEXT))); m_pNextPage->Show(); + m_pNextPage->set_id("next"); AddButton( m_pNextPage, WIZARDDIALOG_BUTTON_STDOFFSET_X ); SetNextButton( m_pNextPage ); @@ -173,6 +175,7 @@ namespace svt m_pFinish->SetSizePixel( LogicToPixel( Size( 50, 14 ), MAP_APPFONT ) ); m_pFinish->SetText(SVT_RESSTR(STR_WIZDLG_FINISH)); m_pFinish->Show(); + m_pFinish->set_id("finish"); AddButton( m_pFinish, WIZARDDIALOG_BUTTON_STDOFFSET_X ); m_pFinish->SetClickHdl( LINK( this, OWizardMachine, OnFinish ) ); diff --git a/vcl/source/control/button.cxx b/vcl/source/control/button.cxx index caf22e4..0546be2 100644 --- a/vcl/source/control/button.cxx +++ b/vcl/source/control/button.cxx @@ -1703,6 +1703,7 @@ void PushButton::ShowFocus(const Rectangle& rRect) void OKButton::ImplInit( vcl::Window* pParent, WinBits nStyle ) { + set_id("ok"); PushButton::ImplInit( pParent, nStyle ); SetText( Button::GetStandardText( StandardButtonType::OK ) ); @@ -1748,6 +1749,7 @@ void OKButton::Click() void CancelButton::ImplInit( vcl::Window* pParent, WinBits nStyle ) { + set_id("cancel"); PushButton::ImplInit( pParent, nStyle ); SetText( Button::GetStandardText( StandardButtonType::Cancel ) ); @@ -1799,6 +1801,7 @@ CloseButton::CloseButton( vcl::Window* pParent, WinBits nStyle ) void HelpButton::ImplInit( vcl::Window* pParent, WinBits nStyle ) { + set_id("help"); PushButton::ImplInit( pParent, nStyle | WB_NOPOINTERFOCUS ); SetText( Button::GetStandardText( StandardButtonType::Help ) ); commit f06c50870c507444177ed604e08884d44f3e9770 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Fri May 13 04:07:00 2016 +0200 Wall is a good idea for the vim ide integration Change-Id: Ifb3c602335097ec1e837b60c236683382cfde3e1 diff --git a/bin/gbuild-to-ide b/bin/gbuild-to-ide index 169cd16..fb2e888 100755 --- a/bin/gbuild-to-ide +++ b/bin/gbuild-to-ide @@ -441,7 +441,7 @@ class VimIntegrationGenerator(IdeIntegrationGenerator): json.dump(global_list, export_file) def generateCommand(self, lib, file): - command = 'clang++ ' + command = 'clang++ -Wall' for key, value in lib.defs.items(): command += ' -D' command += key commit 42237e141b9dca778066f00fa1ca9e83fb27fd8e Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Wed May 11 01:44:17 2016 +0200 uitest: now we can actually enable the ui test demo Change-Id: I18557ea0a7801ba118fd2486338112d8aa917b75 diff --git a/uitest/Module_uitest.mk b/uitest/Module_uitest.mk index 4dbf020..9ebc2f7 100644 --- a/uitest/Module_uitest.mk +++ b/uitest/Module_uitest.mk @@ -12,4 +12,5 @@ $(eval $(call gb_Module_Module,uitest)) $(eval $(call gb_Module_add_uicheck_targets,uitest,\ UITest_calc_demo \ + UITest_demo_ui \ )) commit 8ee75350a9bd5e5b3d4183ef0168c717896f202a Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Wed May 11 01:44:00 2016 +0200 uitest: close all the documents in the tests Change-Id: I4ad9c2603edbf3ac6fc4db60481dc93c16ea63ff diff --git a/uitest/demo_ui/checkbox.py b/uitest/demo_ui/checkbox.py index 8a8bf08..5cc456b 100644 --- a/uitest/demo_ui/checkbox.py +++ b/uitest/demo_ui/checkbox.py @@ -34,6 +34,9 @@ def toggle_checkbox(xContext): xNegativeNumRedCB = xCellsDlg.getChild("negnumred") xNegativeNumRedCB.executeAction("CLICK",tuple()) + okBtn = xCellsDlg.getChild("ok") + okBtn.executeAction("CLICK", tuple()) + ui_test.close_doc() # vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/uitest/demo_ui/combobox.py b/uitest/demo_ui/combobox.py index ba917bb..6df980b 100644 --- a/uitest/demo_ui/combobox.py +++ b/uitest/demo_ui/combobox.py @@ -25,6 +25,9 @@ def select_entry_pos(xContext): actionProps = mkPropertyValues(props) scopeCB.executeAction("SELECT", actionProps) + xCancelBtn = xAddNameDlg.getChild("cancel") + xCancelBtn.executeAction("CLICK", tuple()) + ui_test.close_doc() # vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/uitest/demo_ui/edit.py b/uitest/demo_ui/edit.py index 2b44f20..f418a36 100644 --- a/uitest/demo_ui/edit.py +++ b/uitest/demo_ui/edit.py @@ -39,8 +39,6 @@ def type_text(xContext): xAddBtn = xAddNameDlg.getChild("cancel") xAddBtn.executeAction("CLICK", tuple()) - xUITest.executeCommand(".uno:CloseDoc") - ui_test.close_doc() # vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/uitest/demo_ui/listbox.py b/uitest/demo_ui/listbox.py index 21b19d4..03a4c9e 100644 --- a/uitest/demo_ui/listbox.py +++ b/uitest/demo_ui/listbox.py @@ -25,6 +25,9 @@ def select_entry_pos(xContext): actionProps = mkPropertyValues(props) categoryLB.executeAction("SELECT", actionProps) + xOkBtn = xCellsDlg.getChild("ok") + xOkBtn.executeAction("CLICK", tuple()) + ui_test.close_doc() def select_entry_text(xContext): @@ -44,6 +47,9 @@ def select_entry_text(xContext): actionProps = mkPropertyValues(props) categoryLB.executeAction("SELECT", actionProps) + xOkBtn = xCellsDlg.getChild("ok") + xOkBtn.executeAction("CLICK", tuple()) + ui_test.close_doc() # vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/uitest/demo_ui/tabdialog.py b/uitest/demo_ui/tabdialog.py index 9a6f720..09bf600 100644 --- a/uitest/demo_ui/tabdialog.py +++ b/uitest/demo_ui/tabdialog.py @@ -26,6 +26,9 @@ def select_tab_page_pos(xContext): propsUNO = mkPropertyValues(props) xCellsDlg.executeAction("SELECT", propsUNO) + xOkBtn = xCellsDlg.getChild("ok") + xOkBtn.executeAction("CLICK", tuple()) + ui_test.close_doc() def select_tab_page_name(xContext): @@ -43,6 +46,9 @@ def select_tab_page_name(xContext): propsUNO = mkPropertyValues(props) xCellsDlg.executeAction("SELECT", propsUNO) + xOkBtn = xCellsDlg.getChild("ok") + xOkBtn.executeAction("CLICK", tuple()) + ui_test.close_doc() # vim:set shiftwidth=4 softtabstop=4 expandtab: */ commit 0c5abdea5fe40350df6234e71b70cab1f11764ac Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Wed May 11 01:42:39 2016 +0200 uitest: add method to get all children of a ui object This makes writing ui tests so much easier. Change-Id: Ice7d98c354fc9b68ee4532bc854561b5b9446e3f diff --git a/include/vcl/uitest/uiobject.hxx b/include/vcl/uitest/uiobject.hxx index b9a3f48..f00d80f 100644 --- a/include/vcl/uitest/uiobject.hxx +++ b/include/vcl/uitest/uiobject.hxx @@ -22,6 +22,8 @@ #include <vcl/dllapi.h> +#include <set> + typedef std::map<const OUString, OUString> StringMap; /** @@ -63,6 +65,11 @@ public: virtual std::unique_ptr<UIObject> get_child(const OUString& rID); /** + * Returns a set containing all decendants of the object. + */ + virtual std::set<OUString> get_children() const; + + /** * Currently an internal method to dump the state of the current UIObject as represented by get_state(). * * This method should not be exposed to the outside world. @@ -96,6 +103,8 @@ public: virtual std::unique_ptr<UIObject> get_child(const OUString& rID) override; + virtual std::set<OUString> get_children() const override; + virtual void dumpState() const override; virtual void dumpHierarchy() const override; diff --git a/offapi/com/sun/star/ui/test/XUIObject.idl b/offapi/com/sun/star/ui/test/XUIObject.idl index 9a0ca6b..9409490 100644 --- a/offapi/com/sun/star/ui/test/XUIObject.idl +++ b/offapi/com/sun/star/ui/test/XUIObject.idl @@ -23,6 +23,8 @@ interface XUIObject com::sun::star::beans::PropertyValues getState(); string getType(); + + sequence<string> getChildren(); }; }; }; }; }; }; diff --git a/vcl/source/uitest/uiobject.cxx b/vcl/source/uitest/uiobject.cxx index 2852415..6b4c471 100644 --- a/vcl/source/uitest/uiobject.cxx +++ b/vcl/source/uitest/uiobject.cxx @@ -56,6 +56,11 @@ std::unique_ptr<UIObject> UIObject::get_child(const OUString&) return std::unique_ptr<UIObject>(); } +std::set<OUString> UIObject::get_children() const +{ + return std::set<OUString>(); +} + void UIObject::dumpState() const { } @@ -311,6 +316,29 @@ vcl::Window* findChild(vcl::Window* pParent, const OUString& rID) return nullptr; } +void addChildren(vcl::Window* pParent, std::set<OUString>& rChildren) +{ + if (!pParent) + return; + + size_t nCount = pParent->GetChildCount(); + for (size_t i = 0; i < nCount; ++i) + { + vcl::Window* pChild = pParent->GetChild(i); + if (pChild) + { + OUString aId = pChild->get_id(); + if (!aId.isEmpty()) + { + auto ret = rChildren.insert(aId); + SAL_WARN_IF(!ret.second, "vcl.uitest", "duplicate ids for ui elements. violates locally unique requirement"); + } + + addChildren(pChild, rChildren); + } + } +} + } std::unique_ptr<UIObject> WindowUIObject::get_child(const OUString& rID) @@ -322,6 +350,15 @@ std::unique_ptr<UIObject> WindowUIObject::get_child(const OUString& rID) return aFunction(pWindow); } +std::set<OUString> WindowUIObject::get_children() const +{ + vcl::Window* pDialogParent = get_dialog_parent(mxWindow.get()); + std::set<OUString> aChildren; + aChildren.insert(pDialogParent->get_id()); + addChildren(pDialogParent, aChildren); + return aChildren; +} + OUString WindowUIObject::get_name() const { return OUString("WindowUIObject"); diff --git a/vcl/source/uitest/uno/uiobject_uno.cxx b/vcl/source/uitest/uno/uiobject_uno.cxx index 998a0d9..7c6ca83 100644 --- a/vcl/source/uitest/uno/uiobject_uno.cxx +++ b/vcl/source/uitest/uno/uiobject_uno.cxx @@ -10,6 +10,8 @@ #include "uiobject_uno.hxx" #include <vcl/svapp.hxx> +#include <set> + UIObjectUnoObj::UIObjectUnoObj(std::unique_ptr<UIObject> pObj): UIObjectBase(m_aMutex), mpObj(std::move(pObj)) @@ -69,6 +71,24 @@ css::uno::Sequence<css::beans::PropertyValue> UIObjectUnoObj::getState() return aProps; } +css::uno::Sequence<OUString> UIObjectUnoObj::getChildren() + throw (css::uno::RuntimeException, std::exception) +{ + if (!mpObj) + throw css::uno::RuntimeException(); + + std::set<OUString> aChildren = mpObj->get_children(); + + css::uno::Sequence<OUString> aRet(aChildren.size()); + sal_Int32 i = 0; + for (auto itr = aChildren.begin(), itrEnd = aChildren.end(); itr != itrEnd; ++itr, ++i) + { + aRet[i] = *itr; + } + + return aRet; +} + OUString SAL_CALL UIObjectUnoObj::getType() throw (css::uno::RuntimeException, std::exception) { diff --git a/vcl/source/uitest/uno/uiobject_uno.hxx b/vcl/source/uitest/uno/uiobject_uno.hxx index d3519bf..fe0669a 100644 --- a/vcl/source/uitest/uno/uiobject_uno.hxx +++ b/vcl/source/uitest/uno/uiobject_uno.hxx @@ -46,6 +46,9 @@ public: css::uno::Sequence<css::beans::PropertyValue> SAL_CALL getState() throw (css::uno::RuntimeException, std::exception) override; + css::uno::Sequence<OUString> SAL_CALL getChildren() + throw (css::uno::RuntimeException, std::exception) override; + OUString SAL_CALL getType() throw (css::uno::RuntimeException, std::exception) override; commit 4ec1c63b91ac1f0c77f7ead33b4cbbd9d80a613b Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Tue May 10 01:27:59 2016 +0200 uitest: add the ui demo tests The makefile part needs to be added but the tests currently hang as I'm not closing the dialogs yet. Change-Id: I8f938fb9b46213e6b1c7295bde780f119053447e diff --git a/uitest/demo_ui/demo_ui.txt b/uitest/demo_ui/demo_ui.txt new file mode 100644 index 0000000..6db5b79 --- /dev/null +++ b/uitest/demo_ui/demo_ui.txt @@ -0,0 +1,10 @@ +demo_ui.checkbox.toggle_checkbox +demo_ui.combobox.select_entry_pos +demo_ui.edit.type_text +demo_ui.gridwin.select_cell +demo_ui.gridwin.select_range +demo_ui.gridwin.extend_range +demo_ui.listbox.select_entry_pos +demo_ui.listbox.select_entry_text +demo_ui.tabdialog.select_tab_page_pos +demo_ui.tabdialog.select_tab_page_name commit 40804d6179c42bb39ec70f539f51ecf93934814c Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Tue May 10 01:26:56 2016 +0200 uitest: report when a dialog was not executed correctly Change-Id: Ibe603045b095e020e572bac986d766ac555b0e04 diff --git a/uitest/uitest_helper.py b/uitest/uitest_helper.py index 5d5f158..cac4ea1 100644 --- a/uitest/uitest_helper.py +++ b/uitest/uitest_helper.py @@ -9,6 +9,13 @@ import time from helper import EventListener +class DialogNotExecutedException(Exception): + def __init__(self, command): + self.command = command + + def __str__(self): + return "Dialog not executed for: " + self.command + class UITest(object): DEFAULT_SLEEP = 0.1 @@ -28,8 +35,7 @@ class UITest(object): time_ += self.DEFAULT_SLEEP time.sleep(self.DEFAULT_SLEEP) - # report a failure here - print("failure execute modal dialog") + raise DialogNotExecutedException(command) def execute_modeless_dialog_through_command(self, command): with EventListener(self._xContext, "ModelessDialogVisible") as event: @@ -42,8 +48,7 @@ class UITest(object): time_ += self.DEFAULT_SLEEP time.sleep(self.DEFAULT_SLEEP) - # report a failure here - print("failure execute modeless dialog") + raise DialogNotExecutedException(command) def create_doc_in_start_center(self, app): xStartCenter = self._xUITest.getTopFocusWindow() commit 511f6f85d90884f864b5bf42eedb758841f72957 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Tue May 10 01:26:33 2016 +0200 uitest: make it easier to debug which test is causing issues Change-Id: I10a777d15d99a1fea756160ec39093a2781119b1 diff --git a/uitest/main.py b/uitest/main.py index 4ec8ad5..9cda053 100644 --- a/uitest/main.py +++ b/uitest/main.py @@ -19,6 +19,7 @@ def load_test(name): return obj def generic_test(opts, test_name): + print("executing: " + test_name) connection = PersistentConnection(opts) connection.setUp() xContext = connection.getContext() commit d46da071cb4412b708a54cab8252e56c85a9427d Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Tue May 10 00:56:09 2016 +0200 uitest: add all calc demo tests Change-Id: I33417d49665f48cb20b1fb1dbe20a7a2cbbf5074 diff --git a/uitest/calc_tests/calc_demo.txt b/uitest/calc_tests/calc_demo.txt index fd921da..6ff4e22 100644 --- a/uitest/calc_tests/calc_demo.txt +++ b/uitest/calc_tests/calc_demo.txt @@ -1 +1,5 @@ calc_tests.create_range_name.create_range_name +calc_tests.create_range_name.create_local_range_name +calc_tests.function_wizard.open_function_wizard +calc_tests.gridwindow.input +calc_tests.about_test.test_about_dlg commit 0af2f86a286558c08ad4df87a15f5ba89f19eb01 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Mon May 9 22:09:44 2016 +0200 uitest: add README Change-Id: I9511da3100bda9cedd18f6a4e3765bc6f3fbcb78 diff --git a/uitest/README b/uitest/README new file mode 100644 index 0000000..c941673 --- /dev/null +++ b/uitest/README @@ -0,0 +1 @@ +The code for the UI testing framework and the UI tests. commit 3ead72d365c722f2234ace08fdb3d313f709ace5 Author: Markus Mohrhard <markus.mohrh...@googlemail.com> Date: Mon May 9 10:05:14 2016 +0200 uitest: build system part for new uitests We now can call the uitests with make uitest.uickeck Change-Id: I20c73efd93c7987f3b841cd0e3e7842ee7a5dab9 diff --git a/Makefile.in b/Makefile.in index 5e8b9de..23ccc95 100644 --- a/Makefile.in +++ b/Makefile.in @@ -7,7 +7,7 @@ # file, You can obtain one at http://mozilla.org/MPL/2.0/. # -gb_Top_MODULE_CHECK_TARGETS := slowcheck unitcheck subsequentcheck perfcheck +gb_Top_MODULE_CHECK_TARGETS := slowcheck unitcheck subsequentcheck perfcheck uicheck .PHONY : all check-if-root bootstrap gbuild build build-non-l10n-only build-l10n-only check clean clean-build clean-host test-install distclean distro-pack-install docs download etags fetch findunusedcode get-submodules id install install-strip tags debugrun help showmodules translations packageinfo internal.clean $(gb_Top_MODULE_CHECK_TARGETS) @@ -144,6 +144,7 @@ gbuild_TARGETS := AllLangHelp \ Rdb \ StaticLibrary \ UIConfig \ + UITest \ UnoApi \ UnpackedTarball \ WinResTarget \ diff --git a/RepositoryModule_host.mk b/RepositoryModule_host.mk index d2f1d84..5954a50 100644 --- a/RepositoryModule_host.mk +++ b/RepositoryModule_host.mk @@ -138,6 +138,7 @@ $(eval $(call gb_Module_add_moduledirs,libreoffice,\ ucb \ ucbhelper \ udkapi \ + $(call gb_Helper_optional,PYUNO,uitest) \ UnoControls \ unodevtools \ unoil \ @@ -181,7 +182,7 @@ endef # otherwise cyclic dependencies ruin everything. # do not serialize on a partial build as that may fail due to missing deps. # the default goal is all (see Module.mk) -ifeq (,$(filter-out all build check unitcheck slowcheck subsequentcheck,$(MAKECMDGOALS))) +ifeq (,$(filter-out all build check unitcheck slowcheck subsequentcheck uicheck,$(MAKECMDGOALS))) $(eval $(call repositorymodule_serialize,\ scfilt \ $(call gb_Helper_optional,SCRIPTING,vbaobj) \ diff --git a/solenv/gbuild/Module.mk b/solenv/gbuild/Module.mk index 468b80b..d4217ea 100644 --- a/solenv/gbuild/Module.mk +++ b/solenv/gbuild/Module.mk @@ -27,12 +27,14 @@ # recursive Module/checks # Module/slowcheck run all slow unit tests # Module/subsequentcheck run system tests all system tests +# Module/uicheck run uitests all uitests # recursive Module/subsequentchecks # build (global) build the product top-level Module # unitcheck (global) run unit tests top-level Module/unitcheck # slowcheck (global) run slow unit tests top-level Module/slowcheck # subsequentcheck (global) run system tests top-level Module/subsequentcheck # perfcheck (global) run performance unit tests top-level Module/perfcheck +# uicheck (global) run the uitests run all uitests # all (global) default goal build unitcheck @@ -47,6 +49,7 @@ gb_Module_SLOWCHECKTARGETSTACK := gb_Module_SUBSEQUENTCHECKTARGETSTACK := gb_Module_STAGINGCHECKTARGETSTACK := gb_Module_PERFCHECKTARGETSTACK := +gb_Module_UICHECKTARGETSTACK := gb_Module_CLEANTARGETSTACK := # The currently read gbuild makefile. @@ -68,7 +71,7 @@ $(call gb_Module_get_clean_target,%) : $(call gb_Output_announce,$*,$(false),MOD,5) $(call gb_Output_announce_title,module $* cleared.) -$(call gb_Helper_abbreviate_dirs,\ - rm -f $(call gb_Module_get_target,$*) $(call gb_Module_get_nonl10n_target,$*) $(call gb_Module_get_l10n_target,$*) $(call gb_Module_get_check_target,$*) $(call gb_Module_get_slowcheck_target,$*) $(call gb_Module_get_subsequentcheck_target,$*) $(call gb_Module_get_perfcheck_target,$*)) + rm -f $(call gb_Module_get_target,$*) $(call gb_Module_get_nonl10n_target,$*) $(call gb_Module_get_l10n_target,$*) $(call gb_Module_get_check_target,$*) $(call gb_Module_get_slowcheck_target,$*) $(call gb_Module_get_subsequentcheck_target,$*) $(call gb_Module_get_perfcheck_target,$*) $(call gb_Module_get_uicheck,$*)) $(call gb_Module_get_l10n_target,%) : $(call gb_Output_announce,$*,$(true),LOC,5) @@ -112,6 +115,13 @@ $(call gb_Module_get_perfcheck_target,%) : mkdir -p $(dir $@) && \ touch $@) +$(call gb_Module_get_uicheck_target,%) : + $(call gb_Output_announce,$*,$(true),UIT,5) + $(call gb_Output_announce_title,module $* uicheck done.) + -$(call gb_Helper_abbreviate_dirs,\ + mkdir -p $(dir $@) && \ + touch $@) + $(call gb_Module_get_target,%) : $(call gb_Output_announce,$*,$(true),MOD,5) $(call gb_Output_announce_title,module $* done.) @@ -119,7 +129,7 @@ $(call gb_Module_get_target,%) : mkdir -p $(dir $@) && \ touch $@) ... etc. - the rest is truncated _______________________________________________ Libreoffice-commits mailing list libreoffice-comm...@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/libreoffice-commits