1919
2020import pkg_resources
2121
22- from AnyQt .QtGui import QFont , QColor , QPalette , QDesktopServices
23- from AnyQt .QtWidgets import QMessageBox
22+ from AnyQt .QtGui import QFont , QColor , QPalette , QDesktopServices , QIcon
2423from AnyQt .QtCore import (
2524 Qt , QDir , QUrl , QSettings , QThread , pyqtSignal , QT_VERSION
2625)
3938from Orange .canvas .registry import qt
4039from Orange .canvas .registry import WidgetRegistry , set_global_registry
4140from Orange .canvas .registry import cache
41+ from Orange .canvas .utils .overlay import NotificationWidget , NotificationOverlay
42+ from Orange .widgets import gui
4243
4344log = logging .getLogger (__name__ )
4445
@@ -180,32 +181,56 @@ def make_sql_logger(level=logging.INFO):
180181 sql_log .addHandler (handler )
181182
182183
183- def show_survey ():
184- # If run for the first time, open a browser tab with a survey
185- settings = QSettings ()
186- show_survey = settings .value ("startup/show-survey" , True , type = bool )
184+ def setup_notifications ():
185+ settings = config .settings ()
186+
187+ # If run for the fifth time, prompt short survey
188+ show_survey = settings ["startup/show-short-survey" ] and \
189+ settings ["startup/launch-count" ] >= 5
187190 if show_survey :
188- question = QMessageBox (
189- QMessageBox .Question ,
190- 'Orange Survey' ,
191- 'We would like to know more about how our software is used.\n \n '
192- 'Would you care to fill our short 1-minute survey?' ,
193- QMessageBox .Yes | QMessageBox .No )
194- question .setDefaultButton (QMessageBox .Yes )
195- later = question .addButton ('Ask again later' , QMessageBox .NoRole )
196- question .setEscapeButton (later )
197-
198- def handle_response (result ):
199- if result == QMessageBox .Yes :
191+ surveyDialogButtons = NotificationWidget .Ok | NotificationWidget .Close
192+ surveyDialog = NotificationWidget (icon = QIcon (gui .resource_filename ("icons/information.png" )),
193+ title = "Survey" ,
194+ text = "We want to understand our users better.\n "
195+ "Would you like to take a short survey?" ,
196+ standardButtons = surveyDialogButtons )
197+
198+ def handle_survey_response (button ):
199+ if surveyDialog .buttonRole (button ) == NotificationWidget .AcceptRole :
200200 success = QDesktopServices .openUrl (
201201 QUrl ("https://orange.biolab.si/survey/short.html" ))
202- settings .setValue ("startup/show-survey" , not success )
203- else :
204- settings .setValue ("startup/show-survey" , result != QMessageBox .No )
202+ settings ["startup/show-short-survey" ] = not success
203+ elif surveyDialog .buttonRole (button ) == NotificationWidget .RejectRole :
204+ settings ["startup/show-short-survey" ] = False
205+
206+ surveyDialog .clicked .connect (handle_survey_response )
207+
208+ NotificationOverlay .registerNotification (surveyDialog )
205209
206- question .finished .connect (handle_response )
207- question .show ()
208- return question
210+ # data collection permission
211+ if not settings ["error-reporting/permission-requested" ]:
212+ permDialogButtons = NotificationWidget .Ok | NotificationWidget .Close
213+ permDialog = NotificationWidget (icon = QIcon (gui .resource_filename (
214+ "../../distribute/icon-48.png" )),
215+ title = "Anonymous Usage Statistics" ,
216+ text = "Do you wish to opt-in to sharing "
217+ "statistics about how you use Orange?\n "
218+ "All data is anonymized and used "
219+ "exclusively for understanding how users "
220+ "interact with Orange." ,
221+ standardButtons = permDialogButtons )
222+ btnOK = permDialog .button (NotificationWidget .AcceptRole )
223+ btnOK .setText ("Allow" )
224+
225+ def handle_permission_response (button ):
226+ if permDialog .buttonRole (button ) != permDialog .DismissRole :
227+ settings ["error-reporting/permission-requested" ] = True
228+ if permDialog .buttonRole (button ) == permDialog .AcceptRole :
229+ settings ["error-reporting/send-statistics" ] = True
230+
231+ permDialog .clicked .connect (handle_permission_response )
232+
233+ NotificationOverlay .registerNotification (permDialog )
209234
210235
211236def check_for_updates ():
@@ -249,31 +274,39 @@ def ua_string():
249274
250275 def compare_versions (latest ):
251276 version = pkg_resources .parse_version
252- if version (latest ) <= version (current ):
277+ skipped = settings .value ('startup/latest-skipped-version' , "" , type = str )
278+ if version (latest ) <= version (current ) or \
279+ latest == skipped :
253280 return
254- question = QMessageBox (
255- QMessageBox .Information ,
256- 'Orange Update Available' ,
257- 'A newer version of Orange is available.<br><br>'
258- '<b>Current version:</b> {}<br>'
259- '<b>Latest version:</b> {}' .format (current , latest ),
260- textFormat = Qt .RichText )
261- ok = question .addButton ('Download Now' , question .AcceptRole )
262- question .setDefaultButton (ok )
263- question .addButton ('Remind Later' , question .RejectRole )
264- question .finished .connect (
265- lambda :
266- question .clickedButton () == ok and
267- QDesktopServices .openUrl (QUrl ("https://orange.biolab.si/download/" )))
268- question .show ()
281+
282+ questionButtons = NotificationWidget .Ok | NotificationWidget .Close
283+ question = NotificationWidget (icon = QIcon (gui .resource_filename ('icons/Dlg_down3.png' )),
284+ title = 'Orange Update Available' ,
285+ text = 'Current version: <b>{}</b><br>'
286+ 'Latest version: <b>{}</b>' .format (current , latest ),
287+ textFormat = Qt .RichText ,
288+ standardButtons = questionButtons ,
289+ acceptLabel = "Download" ,
290+ rejectLabel = "Skip this Version" )
291+
292+ def handle_click (b ):
293+ if question .buttonRole (b ) != question .DismissRole :
294+ settings .setValue ('startup/latest-skipped-version' , latest )
295+ if question .buttonRole (b ) == question .AcceptRole :
296+ QDesktopServices .openUrl (QUrl ("https://orange.biolab.si/download/" ))
297+
298+ question .clicked .connect (handle_click )
299+
300+ NotificationOverlay .registerNotification (question )
269301
270302 thread = GetLatestVersion ()
271303 thread .resultReady .connect (compare_versions )
272304 thread .start ()
273305 return thread
306+ return None
274307
275- def send_usage_statistics ():
276308
309+ def send_usage_statistics ():
277310 class SendUsageStatistics (QThread ):
278311 def run (self ):
279312 try :
@@ -287,6 +320,7 @@ def run(self):
287320 thread .start ()
288321 return thread
289322
323+
290324def main (argv = None ):
291325 if argv is None :
292326 argv = sys .argv
@@ -433,6 +467,8 @@ def onrequest(url):
433467
434468 settings = QSettings ()
435469
470+ settings .setValue ('startup/launch-count' , settings .value ('startup/launch-count' , 0 , int ) + 1 )
471+
436472 stylesheet = options .stylesheet or defaultstylesheet
437473 stylesheet_string = None
438474
@@ -557,8 +593,10 @@ def show_message(message):
557593 open_requests [- 1 ])
558594 canvas_window .load_scheme (open_requests [- 1 ].toLocalFile ())
559595
596+ # initialize notifications
597+ setup_notifications ()
598+
560599 # local references prevent destruction
561- survey = show_survey ()
562600 update_check = check_for_updates ()
563601 send_stat = send_usage_statistics ()
564602
@@ -591,7 +629,6 @@ def show_message(message):
591629 status = 42
592630
593631 del canvas_window
594- del survey
595632 del update_check
596633 del send_stat
597634
0 commit comments