1 // Copyright 2014 PDFium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 // Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com 6 7 #include "fpdfsdk/formfiller/cffl_radiobutton.h" 8 9 #include "fpdfsdk/cpdfsdk_formfillenvironment.h" 10 #include "fpdfsdk/cpdfsdk_widget.h" 11 #include "fpdfsdk/formfiller/cffl_formfiller.h" 12 #include "fpdfsdk/pwl/cpwl_special_button.h" 13 #include "public/fpdf_fwlevent.h" 14 15 CFFL_RadioButton::CFFL_RadioButton(CPDFSDK_FormFillEnvironment* pApp, 16 CPDFSDK_Widget* pWidget) 17 : CFFL_Button(pApp, pWidget) {} 18 19 CFFL_RadioButton::~CFFL_RadioButton() {} 20 21 CPWL_Wnd* CFFL_RadioButton::NewPDFWindow(const CPWL_Wnd::CreateParams& cp) { 22 auto* pWnd = new CPWL_RadioButton(); 23 pWnd->Create(cp); 24 pWnd->SetCheck(m_pWidget->IsChecked()); 25 return pWnd; 26 } 27 28 bool CFFL_RadioButton::OnKeyDown(CPDFSDK_Annot* pAnnot, 29 uint32_t nKeyCode, 30 uint32_t nFlags) { 31 switch (nKeyCode) { 32 case FWL_VKEY_Return: 33 case FWL_VKEY_Space: 34 return true; 35 default: 36 return CFFL_FormFiller::OnKeyDown(pAnnot, nKeyCode, nFlags); 37 } 38 } 39 40 bool CFFL_RadioButton::OnChar(CPDFSDK_Annot* pAnnot, 41 uint32_t nChar, 42 uint32_t nFlags) { 43 switch (nChar) { 44 case FWL_VKEY_Return: 45 case FWL_VKEY_Space: { 46 CPDFSDK_PageView* pPageView = pAnnot->GetPageView(); 47 ASSERT(pPageView); 48 49 CPDFSDK_Annot::ObservedPtr pObserved(m_pWidget.Get()); 50 if (m_pFormFillEnv->GetInteractiveFormFiller()->OnButtonUp( 51 &pObserved, pPageView, nFlags) || 52 !pObserved) { 53 return true; 54 } 55 56 CFFL_FormFiller::OnChar(pAnnot, nChar, nFlags); 57 CPWL_RadioButton* pWnd = GetRadioButton(pPageView, true); 58 if (pWnd) 59 pWnd->SetCheck(true); 60 return CommitData(pPageView, nFlags); 61 } 62 default: 63 return CFFL_FormFiller::OnChar(pAnnot, nChar, nFlags); 64 } 65 } 66 67 bool CFFL_RadioButton::OnLButtonUp(CPDFSDK_PageView* pPageView, 68 CPDFSDK_Annot* pAnnot, 69 uint32_t nFlags, 70 const CFX_PointF& point) { 71 CFFL_Button::OnLButtonUp(pPageView, pAnnot, nFlags, point); 72 73 if (!IsValid()) 74 return true; 75 76 CPWL_RadioButton* pWnd = GetRadioButton(pPageView, true); 77 if (pWnd) 78 pWnd->SetCheck(true); 79 80 return CommitData(pPageView, nFlags); 81 } 82 83 bool CFFL_RadioButton::IsDataChanged(CPDFSDK_PageView* pPageView) { 84 CPWL_RadioButton* pWnd = GetRadioButton(pPageView, false); 85 return pWnd && pWnd->IsChecked() != m_pWidget->IsChecked(); 86 } 87 88 void CFFL_RadioButton::SaveData(CPDFSDK_PageView* pPageView) { 89 CPWL_RadioButton* pWnd = GetRadioButton(pPageView, false); 90 if (!pWnd) 91 return; 92 93 bool bNewChecked = pWnd->IsChecked(); 94 95 if (bNewChecked) { 96 CPDF_FormField* pField = m_pWidget->GetFormField(); 97 for (int32_t i = 0, sz = pField->CountControls(); i < sz; i++) { 98 if (CPDF_FormControl* pCtrl = pField->GetControl(i)) { 99 if (pCtrl->IsChecked()) { 100 break; 101 } 102 } 103 } 104 } 105 CPDFSDK_Widget::ObservedPtr observed_widget(m_pWidget.Get()); 106 CFFL_RadioButton::ObservedPtr observed_this(this); 107 108 m_pWidget->SetCheck(bNewChecked, false); 109 if (!observed_widget) 110 return; 111 m_pWidget->UpdateField(); 112 if (!observed_widget || !observed_this) 113 return; 114 SetChangeMark(); 115 } 116 117 CPWL_RadioButton* CFFL_RadioButton::GetRadioButton(CPDFSDK_PageView* pPageView, 118 bool bNew) { 119 return static_cast<CPWL_RadioButton*>(GetPDFWindow(pPageView, bNew)); 120 } 121