Ticket #3973: MythVideoParentalControls

File MythVideoParentalControls, 14.0 KB (added by Doug Young <goofdad@…>, 13 years ago)

patch

Line 
1Index: mythvideo/mythvideo/videodlg.h
2===================================================================
3--- mythvideo/mythvideo/videodlg.h      (revision 14422)
4+++ mythvideo/mythvideo/videodlg.h      (working copy)
5@@ -84,4 +84,39 @@
6     int m_exit_type;
7 };
8 
9+class MPUBLIC MythMultiPasswordDialog: public MythDialog
10+{
11+Q_OBJECT
12+   
13+    //
14+    //  Very simple class, not themeable
15+    //
16+   
17+public:
18+   
19+    MythMultiPasswordDialog( QString message,
20+                             bool *success,
21+                             int numTargets,
22+                             QString *targets,
23+                             MythMainWindow *parent,
24+                             const char *name = 0,
25+                             bool setsize = true);
26+    ~MythMultiPasswordDialog();
27+   
28+public slots:
29+             
30+    void checkPasswords(const QString &);
31+   
32+protected:
33+   
34+    void keyPressEvent(QKeyEvent *e);
35+   
36+private:
37+   
38+    MythLineEdit        *m_passwordEditor;
39+    int                 m_numTargets;
40+    QString             *m_targetList;
41+    bool                *m_success;
42+};
43+
44 #endif
45Index: mythvideo/mythvideo/globalsettings.cpp
46===================================================================
47--- mythvideo/mythvideo/globalsettings.cpp      (revision 14422)
48+++ mythvideo/mythvideo/globalsettings.cpp      (working copy)
49@@ -43,14 +43,36 @@
50 HostLineEdit *VideoAdminPassword()
51 {
52     HostLineEdit *gc = new HostLineEdit("VideoAdminPassword");
53-    gc->setLabel(QObject::tr("Parental Control PIN"));
54-    gc->setHelpText(QObject::tr("This PIN is used to control the current "
55-                    "Parental Level. If you want to use this feature, then "
56-                    "setting the value to all numbers will make your life much "
57-                    "easier."));
58+    gc->setLabel(QObject::tr("Parental Level 4 PIN"));
59+    gc->setHelpText(QObject::tr("This PIN is used to enter Parental Control "
60+                    "level 4 as well as the Video Mmanager. "
61+                    "Setting this value to all numbers will make your life "
62+                    "much easier."));
63     return gc;
64 }
65 
66+HostLineEdit *VideoAdminPasswordThree()
67+{
68+    HostLineEdit *gc = new HostLineEdit("VideoAdminPasswordThree");
69+    gc->setLabel(QObject::tr("Parental Level 3 PIN"));
70+    gc->setHelpText(QObject::tr("This PIN is used to enter Parental Control "
71+                    "level 3. "
72+                    "Setting this value to all numbers will make your life "
73+                    "much easier."));
74+    return gc;
75+}
76+
77+HostLineEdit *VideoAdminPasswordTwo()
78+{
79+    HostLineEdit *gc = new HostLineEdit("VideoAdminPasswordTwo");
80+    gc->setLabel(QObject::tr("Parental Level 2 PIN"));
81+    gc->setHelpText(QObject::tr("This PIN is used to enter Parental Control "
82+                    "level 2. "
83+                    "Setting this value to all numbers will make your life "
84+                    "much easier."));
85+    return gc;
86+}
87+
88 HostCheckBox *VideoAggressivePC()
89 {
90     HostCheckBox *gc = new HostCheckBox("VideoAggressivePC");
91@@ -550,16 +572,13 @@
92 
93 VideoGeneralSettings::VideoGeneralSettings()
94 {
95-    const int pages = 5;
96+    const int pages = 6;
97 
98     VerticalConfigurationGroup *general = new VerticalConfigurationGroup(false);
99     general->setLabel(QObject::tr("General Settings (%1/%2)")
100                       .arg(1).arg(pages));
101     general->addChild(VideoStartupDirectory());
102     general->addChild(VideoArtworkDirectory());
103-    general->addChild(VideoDefaultParentalLevel());
104-    general->addChild(VideoAdminPassword());
105-    general->addChild(VideoAggressivePC());
106     general->addChild(VideoDefaultView());
107     addChild(general);
108 
109@@ -616,6 +635,20 @@
110     vgal->addChild(VideoGalleryAspectRatio());
111     general5->addChild(vgal);
112     addChild(general5);
113+
114+    VerticalConfigurationGroup *general6 =
115+            new VerticalConfigurationGroup(false);
116+    general6->setLabel(QObject::tr("General Settings (%1/%2)")
117+                       .arg(6).arg(pages));
118+    VerticalConfigurationGroup *pctrl =
119+            new VerticalConfigurationGroup(true, false);
120+    pctrl->addChild(VideoDefaultParentalLevel());
121+    pctrl->addChild(VideoAdminPassword());
122+    pctrl->addChild(VideoAdminPasswordThree());
123+    pctrl->addChild(VideoAdminPasswordTwo());
124+    pctrl->addChild(VideoAggressivePC());
125+    general6->addChild(pctrl);
126+    addChild(general6);
127 }
128 
129 VideoPlayerSettings::VideoPlayerSettings()
130Index: mythvideo/mythvideo/main.cpp
131===================================================================
132--- mythvideo/mythvideo/main.cpp        (revision 14422)
133+++ mythvideo/mythvideo/main.cpp        (working copy)
134@@ -81,7 +81,7 @@
135       private:
136         static int runVideoManager(VideoList *video_list)
137         {
138-            if (checkParentPassword())
139+            if (checkParentPassword(4))
140             {
141                 VideoScanner scanner;
142                 scanner.doScan(GetVideoDirs());
143@@ -473,7 +473,7 @@
144 
145             if (gContext->GetNumSetting("VideoAggressivePC", 0))
146             {
147-                if (checkParentPassword())
148+                if (checkParentPassword(4))
149                 {
150                     VideoGeneralSettings settings;
151                     settings.exec();
152Index: mythvideo/mythvideo/videotree.cpp
153===================================================================
154--- mythvideo/mythvideo/videotree.cpp   (revision 14422)
155+++ mythvideo/mythvideo/videotree.cpp   (working copy)
156@@ -347,7 +347,7 @@
157         which_level = 4;
158     }
159 
160-    if (checkParentPassword())
161+    if (checkParentPassword(which_level, current_parental_level))
162     {
163         current_parental_level = which_level;
164         checkedSetText(m_imp->pl_value,
165Index: mythvideo/mythvideo/videoutils.cpp
166===================================================================
167--- mythvideo/mythvideo/videoutils.cpp  (revision 14422)
168+++ mythvideo/mythvideo/videoutils.cpp  (working copy)
169@@ -5,6 +5,8 @@
170 
171 #include "globals.h"
172 #include "videoutils.h"
173+#include "videotree.h"
174+#include "videodlg.h"
175 #include "metadata.h"
176 #include "metadatalistmanager.h"
177 
178@@ -54,18 +56,64 @@
179     while (item && playing_time.elapsed() > WATCHED_WATERMARK);
180 }
181 
182-bool checkParentPassword()
183+bool checkParentPassword(int which_level, int current_parental_level)
184 {
185     QDateTime curr_time = QDateTime::currentDateTime();
186     QString last_time_stamp = gContext->GetSetting("VideoPasswordTime");
187-    QString password = gContext->GetSetting("VideoAdminPassword");
188+    QString last_parent_lvl = gContext->GetSetting("VideoPasswordLevel");
189+    QString passwords[3];
190+    passwords[0] = gContext->GetSetting("VideoAdminPassword");
191+    passwords[1] = gContext->GetSetting("VideoAdminPasswordThree");
192+    passwords[2] = gContext->GetSetting("VideoAdminPasswordTwo");
193 
194-    if (password.length() < 1)
195+    // check that settings are valid...
196+    // bubble up passwords set at a lower level, because that doesn't
197+    // make sense.
198+    //
199+    // This is a best guess as to what the user meant ;-)
200+
201+    bool fixSettings = false;
202+
203+    if ((passwords[1].length() == 0) &&
204+       (passwords[2].length() > 0))
205+    {
206+       passwords[1] = passwords[2];
207+       fixSettings = true;
208+    }
209+
210+    if ((passwords[0].length() == 0) &&
211+       (passwords[1].length() > 0))
212+    {
213+       passwords[0] = passwords[1];
214+       fixSettings = true;
215+    }
216+
217+    if (fixSettings)
218+    {
219+       gContext->SetSetting("VideoAdminPassword", passwords[0]);
220+       gContext->SaveSetting("VideoAdminPassword", passwords[0]);
221+       gContext->SetSetting("VideoAdminPasswordThree", passwords[1]);
222+       gContext->SaveSetting("VideoAdminPasswordThree", passwords[1]);
223+       gContext->SetSetting("VideoAdminPasswordTwo", passwords[2]);
224+       gContext->SaveSetting("VideoAdminPasswordTwo", passwords[2]);
225+    }
226+
227+    // no password for level 1
228+    if (which_level == 1)
229+       return true;
230+
231+    // You can always switch down from your current level
232+    if (which_level < current_parental_level)
233+       return true;
234+
235+    // if there is no password for your new level
236+    if (passwords[4 - which_level].length() < 1)
237         return true;
238 
239     // See if we recently (and succesfully) asked for a password
240 
241-    if (last_time_stamp.length() < 1)
242+    if ((last_time_stamp.length() < 1) ||
243+       (last_parent_lvl.length() < 1))
244     {
245         // Probably first time used
246 
247@@ -77,40 +125,45 @@
248     else
249     {
250         QDateTime last_time = QDateTime::fromString(last_time_stamp,
251-                                                    Qt::TextDate);
252-        if (last_time.secsTo(curr_time) < 120)
253+                                                    Qt::ISODate);
254+
255+       int last_level = last_parent_lvl.toInt();
256+
257+        if ((last_level >= which_level) &&
258+           (last_time.secsTo(curr_time) < 120))
259         {
260             // Two minute window
261-            last_time_stamp = curr_time.toString(Qt::TextDate);
262+            last_time_stamp = curr_time.toString(Qt::ISODate);
263             gContext->SetSetting("VideoPasswordTime", last_time_stamp);
264             gContext->SaveSetting("VideoPasswordTime", last_time_stamp);
265             return true;
266         }
267     }
268 
269-    // See if there is a password set
270+    // If we got here, there is a password, and there's no backing down.
271 
272-    if (password.length() > 0)
273+    bool ok = false;
274+    MythMultiPasswordDialog *pwd =
275+       new MythMultiPasswordDialog(QObject::tr("Parental Pin:"),
276+                                   &ok,
277+                                   4 - which_level + 1,
278+                                   passwords,
279+                                   gContext->GetMainWindow());
280+    pwd->exec();
281+    delete pwd;
282+   
283+    if (ok)
284     {
285-        bool ok = false;
286-        MythPasswordDialog *pwd =
287-                new MythPasswordDialog(QObject::tr("Parental Pin:"), &ok,
288-                                       password, gContext->GetMainWindow());
289-        pwd->exec();
290-        delete pwd;
291-
292-        if (ok)
293-        {
294-            // All is good
295-            last_time_stamp = curr_time.toString(Qt::TextDate);
296-            gContext->SetSetting("VideoPasswordTime", last_time_stamp);
297-            gContext->SaveSetting("VideoPasswordTime", last_time_stamp);
298-            return true;
299-        }
300+       // All is good
301+       last_time_stamp = curr_time.toString(Qt::ISODate);
302+       last_parent_lvl = QString::number(which_level);
303+       gContext->SetSetting("VideoPasswordTime", last_time_stamp);
304+       gContext->SaveSetting("VideoPasswordTime", last_time_stamp);
305+       gContext->SetSetting("VideoPasswordLevel", last_parent_lvl);
306+       gContext->SaveSetting("VideoPasswordLevel", last_parent_lvl);
307+       return true;
308     }
309-    else
310-        return true;
311-
312+   
313     return false;
314 }
315 
316Index: mythvideo/mythvideo/videodlg.cpp
317===================================================================
318--- mythvideo/mythvideo/videodlg.cpp    (revision 14422)
319+++ mythvideo/mythvideo/videodlg.cpp    (working copy)
320@@ -205,7 +205,7 @@
321     if (which_level > 4)
322         which_level = 4;
323 
324-    if ((which_level > currentParentalLevel) && !checkParentPassword())
325+    if (!checkParentPassword(which_level, currentParentalLevel))
326         which_level = currentParentalLevel;
327 
328 
329@@ -311,3 +311,84 @@
330     setExitType(SCREEN_EXIT_VIA_JUMP);
331     gContext->GetMainWindow()->JumpTo(location);
332 }
333+
334+/*
335+---------------------------------------------------------------------
336+*/
337+
338+MythMultiPasswordDialog::MythMultiPasswordDialog(QString message,
339+                                                 bool *success,
340+                                                 int numTargets,
341+                                                 QString *targets,
342+                                                 MythMainWindow *parent,
343+                                                 const char *name,
344+                                                 bool)
345+  :MythDialog(parent, name, false)
346+{
347+    int textWidth =  fontMetrics().width(message);
348+    int totalWidth = textWidth + 175;
349+
350+    m_success = success;
351+    m_numTargets = numTargets;
352+    m_targetList = targets;
353+
354+    gContext->GetScreenSettings(screenwidth, wmult, screenheight, hmult);
355+    this->setGeometry((screenwidth - 250 ) / 2,
356+                      (screenheight - 50 ) / 2,
357+                      totalWidth,50);
358+    QFrame *outside_border = new QFrame(this);
359+    outside_border->setGeometry(0,0,totalWidth,50);
360+    outside_border->setFrameStyle(QFrame::Panel | QFrame::Raised );
361+    outside_border->setLineWidth(4);
362+    QLabel *message_label = new QLabel(message, this);
363+    message_label->setAlignment(Qt::AlignRight | Qt::AlignVCenter);
364+    message_label->setGeometry(15,10,textWidth,30);
365+    message_label->setBackgroundOrigin(ParentOrigin);
366+    m_passwordEditor = new MythLineEdit(this);
367+    m_passwordEditor->setEchoMode(QLineEdit::Password);
368+    m_passwordEditor->setGeometry(textWidth + 20,10,135,30);
369+    m_passwordEditor->setBackgroundOrigin(ParentOrigin);
370+    m_passwordEditor->setAllowVirtualKeyboard(false);
371+    connect(m_passwordEditor, SIGNAL(textChanged(const QString &)),
372+            this, SLOT(checkPasswords(const QString &)));
373+
374+    this->setActiveWindow();
375+    m_passwordEditor->setFocus();
376+}
377+
378+void MythMultiPasswordDialog::keyPressEvent(QKeyEvent *e)
379+{
380+    bool handled = false;
381+    QStringList actions;
382+    if (gContext->GetMainWindow()->TranslateKeyPress("qt", e, actions))
383+    {
384+        for (unsigned int i = 0; i < actions.size() && !handled; i++)
385+        {
386+            QString action = actions[i];
387+            if (action == "ESCAPE")
388+            {
389+                handled = true;
390+                MythDialog::keyPressEvent(e);
391+            }
392+        }
393+    }
394+}
395+
396+
397+void MythMultiPasswordDialog::checkPasswords(const QString &the_text)
398+{
399+   
400+    for (int i = 0; i < m_numTargets; i++)
401+    {
402+        if (the_text == m_targetList[i])
403+        {
404+            *m_success = true;
405+            done(0);
406+        }
407+    }
408+}
409+
410+MythMultiPasswordDialog::~MythMultiPasswordDialog()
411+{
412+}
413+
414Index: mythvideo/mythvideo/videoutils.h
415===================================================================
416--- mythvideo/mythvideo/videoutils.h    (revision 14422)
417+++ mythvideo/mythvideo/videoutils.h    (working copy)
418@@ -12,7 +12,7 @@
419     if (item) item->SetText(text);
420 }
421 
422-bool checkParentPassword();
423+bool checkParentPassword(int which_level, int current_parental_level = 0);
424 
425 QStringList GetVideoDirs();
426