Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
5 : * This Source Code Form is subject to the terms of the Mozilla Public
6 : * License, v. 2.0. If a copy of the MPL was not distributed with this
7 : * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
11 : * Licensed to the Apache Software Foundation (ASF) under one or more
12 : * contributor license agreements. See the NOTICE file distributed
13 : * with this work for additional information regarding copyright
14 : * ownership. The ASF licenses this file to you under the Apache
15 : * License, Version 2.0 (the "License"); you may not use this file
16 : * except in compliance with the License. You may obtain a copy of
17 : * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 : */
19 :
20 : #include <hintids.hxx>
21 : #include <com/sun/star/lang/XMultiServiceFactory.hpp>
22 : #include <comphelper/processfactory.hxx>
23 : #include <editeng/unolingu.hxx>
24 : #include <unotools/localedatawrapper.hxx>
25 : #include <i18nlangtag/lang.h>
26 : #include <svl/zformat.hxx>
27 : #include <svl/eitem.hxx>
28 : #include <svx/svxids.hrc>
29 : #include <svx/numinf.hxx>
30 : #include <vcl/msgbox.hxx>
31 : #include <svx/flagsdef.hxx>
32 : #include <svl/itemset.hxx>
33 : #include <docsh.hxx>
34 : #include <swtypes.hxx>
35 : #include <swmodule.hxx>
36 : #include <view.hxx>
37 : #include <wrtsh.hxx>
38 : #include <numfmtlb.hxx>
39 : #include <utlui.hrc>
40 : #include "swabstdlg.hxx"
41 : #include "dialog.hrc"
42 : #include <unomid.h>
43 : #include <sfx2/viewfrm.hxx>
44 :
45 : using namespace ::com::sun::star::uno;
46 : using namespace ::com::sun::star::lang;
47 :
48 : // STATIC DATA
49 :
50 : /**
51 : * Description:
52 : * nFormatType: Display the formats of this Type
53 : * nDefFmt: Select this format and possibly insert it
54 : */
55 :
56 0 : NumFormatListBox::NumFormatListBox(Window* pWin, WinBits nStyle) :
57 : ListBox ( pWin, nStyle ),
58 : nCurrFormatType (-1),
59 : nStdEntry (0),
60 : bOneArea (sal_False),
61 : nDefFormat (0),
62 : pVw (0),
63 : pOwnFormatter (0),
64 : bShowLanguageControl(sal_False),
65 0 : bUseAutomaticLanguage(sal_True)
66 : {
67 0 : Init(NUMBERFORMAT_NUMBER, true);
68 0 : }
69 :
70 0 : extern "C" SAL_DLLPUBLIC_EXPORT Window* SAL_CALL makeNumFormatListBox(Window *pParent, VclBuilder::stringmap &rMap)
71 : {
72 0 : WinBits nBits = WB_LEFT|WB_VCENTER|WB_3DLOOK;
73 :
74 0 : bool bDropdown = VclBuilder::extractDropdown(rMap);
75 :
76 0 : if (bDropdown)
77 0 : nBits |= WB_DROPDOWN;
78 : else
79 0 : nBits |= WB_BORDER;
80 :
81 0 : NumFormatListBox* pListBox = new NumFormatListBox(pParent, nBits|WB_SIMPLEMODE);
82 :
83 0 : if (bDropdown)
84 0 : pListBox->EnableAutoSize(true);
85 :
86 0 : return pListBox;
87 : }
88 :
89 0 : void NumFormatListBox::Init(short nFormatType, sal_Bool bUsrFmts)
90 : {
91 0 : SwView *pView = GetView();
92 :
93 0 : if (pView)
94 0 : eCurLanguage = pView->GetWrtShell().GetCurLang();
95 : else
96 0 : eCurLanguage = SvtSysLocale().GetLanguageTag().getLanguageType();
97 :
98 0 : if (bUsrFmts == sal_False)
99 : {
100 0 : pOwnFormatter = new SvNumberFormatter(comphelper::getProcessComponentContext(), eCurLanguage);
101 : }
102 :
103 0 : SetFormatType(nFormatType);
104 0 : SetDefFormat(nDefFormat);
105 :
106 0 : SetSelectHdl(LINK(this, NumFormatListBox, SelectHdl));
107 0 : }
108 :
109 0 : NumFormatListBox::~NumFormatListBox()
110 : {
111 0 : delete pOwnFormatter;
112 0 : }
113 :
114 0 : SwView* NumFormatListBox::GetView()
115 : {
116 0 : if( pVw )
117 0 : return pVw;
118 0 : return ::GetActiveView();
119 : }
120 :
121 0 : void NumFormatListBox::SetFormatType(const short nFormatType)
122 : {
123 0 : if (nCurrFormatType == -1 ||
124 0 : (nCurrFormatType & nFormatType) == 0) // there are mixed formats, like for example DateTime
125 : {
126 : SvNumberFormatter* pFormatter;
127 :
128 0 : if( pOwnFormatter )
129 0 : pFormatter = pOwnFormatter;
130 : else
131 : {
132 0 : SwView *pView = GetView();
133 : OSL_ENSURE(pView, "no view found");
134 0 : if(!pView)
135 0 : return;
136 0 : SwWrtShell &rSh = pView->GetWrtShell();
137 0 : pFormatter = rSh.GetNumberFormatter();
138 : }
139 :
140 0 : Clear(); // Remove all entries from the Listbox
141 :
142 0 : NfIndexTableOffset eOffsetStart = NF_NUMBER_START;
143 0 : NfIndexTableOffset eOffsetEnd = NF_NUMBER_START;
144 :
145 0 : switch( nFormatType )
146 : {
147 : case NUMBERFORMAT_NUMBER:
148 0 : eOffsetStart=NF_NUMBER_START;
149 0 : eOffsetEnd=NF_NUMBER_END;
150 0 : break;
151 :
152 : case NUMBERFORMAT_PERCENT:
153 0 : eOffsetStart=NF_PERCENT_START;
154 0 : eOffsetEnd=NF_PERCENT_END;
155 0 : break;
156 :
157 : case NUMBERFORMAT_CURRENCY:
158 0 : eOffsetStart=NF_CURRENCY_START;
159 0 : eOffsetEnd=NF_CURRENCY_END;
160 0 : break;
161 :
162 : case NUMBERFORMAT_DATETIME:
163 0 : eOffsetStart=NF_DATE_START;
164 0 : eOffsetEnd=NF_TIME_END;
165 0 : break;
166 :
167 : case NUMBERFORMAT_DATE:
168 0 : eOffsetStart=NF_DATE_START;
169 0 : eOffsetEnd=NF_DATE_END;
170 0 : break;
171 :
172 : case NUMBERFORMAT_TIME:
173 0 : eOffsetStart=NF_TIME_START;
174 0 : eOffsetEnd=NF_TIME_END;
175 0 : break;
176 :
177 : case NUMBERFORMAT_SCIENTIFIC:
178 0 : eOffsetStart=NF_SCIENTIFIC_START;
179 0 : eOffsetEnd=NF_SCIENTIFIC_END;
180 0 : break;
181 :
182 : case NUMBERFORMAT_FRACTION:
183 0 : eOffsetStart=NF_FRACTION_START;
184 0 : eOffsetEnd=NF_FRACTION_END;
185 0 : break;
186 :
187 : case NUMBERFORMAT_LOGICAL:
188 0 : eOffsetStart=NF_BOOLEAN;
189 0 : eOffsetEnd=NF_BOOLEAN;
190 0 : break;
191 :
192 : case NUMBERFORMAT_TEXT:
193 0 : eOffsetStart=NF_TEXT;
194 0 : eOffsetEnd=NF_TEXT;
195 0 : break;
196 :
197 : case NUMBERFORMAT_ALL:
198 0 : eOffsetStart=NF_NUMERIC_START;
199 0 : eOffsetEnd = NfIndexTableOffset( NF_INDEX_TABLE_ENTRIES - 1 );
200 0 : break;
201 :
202 : default:
203 : OSL_FAIL("what a format?");
204 0 : break;
205 : }
206 :
207 : const SvNumberformat* pFmt;
208 0 : sal_uInt16 nPos, i = 0;
209 : sal_uLong nFormat;
210 : Color* pCol;
211 0 : double fVal = GetDefValue( nFormatType );
212 0 : OUString sValue;
213 :
214 : sal_uLong nSysNumFmt = pFormatter->GetFormatIndex(
215 0 : NF_NUMBER_SYSTEM, eCurLanguage );
216 : sal_uLong nSysShortDateFmt = pFormatter->GetFormatIndex(
217 0 : NF_DATE_SYSTEM_SHORT, eCurLanguage );
218 : sal_uLong nSysLongDateFmt = pFormatter->GetFormatIndex(
219 0 : NF_DATE_SYSTEM_LONG, eCurLanguage );
220 :
221 0 : for( long nIndex = eOffsetStart; nIndex <= eOffsetEnd; ++nIndex )
222 : {
223 : nFormat = pFormatter->GetFormatIndex(
224 0 : (NfIndexTableOffset)nIndex, eCurLanguage );
225 0 : pFmt = pFormatter->GetEntry( nFormat );
226 :
227 0 : if( nFormat == pFormatter->GetFormatIndex( NF_NUMBER_STANDARD,
228 0 : eCurLanguage )
229 0 : || ((SvNumberformat*)pFmt)->GetOutputString( fVal, sValue, &pCol )
230 0 : || nFormatType == NUMBERFORMAT_UNDEFINED )
231 : {
232 0 : sValue = pFmt->GetFormatstring();
233 : }
234 0 : else if( nFormatType == NUMBERFORMAT_TEXT )
235 : {
236 0 : pFormatter->GetOutputString( "\"ABC\"", nFormat, sValue, &pCol);
237 : }
238 :
239 0 : if (nFormat != nSysNumFmt &&
240 0 : nFormat != nSysShortDateFmt &&
241 : nFormat != nSysLongDateFmt)
242 : {
243 0 : nPos = InsertEntry( sValue );
244 0 : SetEntryData( nPos, (void*)nFormat );
245 :
246 0 : if( nFormat == pFormatter->GetStandardFormat(
247 0 : nFormatType, eCurLanguage ) )
248 0 : nStdEntry = i;
249 0 : ++i;
250 : }
251 : }
252 :
253 0 : if (!pOwnFormatter)
254 : {
255 0 : nPos = InsertEntry(SW_RESSTR( STR_DEFINE_NUMBERFORMAT ));
256 0 : SetEntryData( nPos, NULL );
257 : }
258 :
259 0 : SelectEntryPos( nStdEntry );
260 :
261 0 : nCurrFormatType = nFormatType;
262 : }
263 : }
264 :
265 0 : void NumFormatListBox::SetDefFormat(const sal_uLong nDefFmt)
266 : {
267 0 : if (nDefFmt == ULONG_MAX)
268 : {
269 0 : nDefFormat = nDefFmt;
270 0 : return;
271 : }
272 :
273 : SvNumberFormatter* pFormatter;
274 0 : if (pOwnFormatter)
275 0 : pFormatter = pOwnFormatter;
276 : else
277 : {
278 0 : SwView *pView = GetView();
279 : OSL_ENSURE(pView, "no view found");
280 0 : if(!pView)
281 0 : return;
282 0 : SwWrtShell &rSh = pView->GetWrtShell();
283 0 : pFormatter = rSh.GetNumberFormatter();
284 : }
285 :
286 0 : short nType = pFormatter->GetType(nDefFmt);
287 :
288 0 : SetFormatType(nType);
289 :
290 0 : sal_uLong nFormat = pFormatter->GetFormatForLanguageIfBuiltIn(nDefFmt, eCurLanguage);
291 :
292 0 : for (sal_uInt16 i = 0; i < GetEntryCount(); i++)
293 : {
294 0 : if (nFormat == (sal_uLong)GetEntryData(i))
295 : {
296 0 : SelectEntryPos(i);
297 0 : nStdEntry = i;
298 0 : nDefFormat = GetFormat();
299 0 : return;
300 : }
301 : }
302 :
303 : // No entry found:
304 0 : double fValue = GetDefValue(nType);
305 0 : OUString sValue;
306 0 : Color* pCol = 0;
307 :
308 0 : if (nType == NUMBERFORMAT_TEXT)
309 : {
310 0 : pFormatter->GetOutputString("\"ABC\"", nDefFmt, sValue, &pCol);
311 : }
312 : else
313 : {
314 0 : pFormatter->GetOutputString(fValue, nDefFmt, sValue, &pCol);
315 : }
316 :
317 0 : sal_uInt16 nPos = 0;
318 0 : while ((sal_uLong)GetEntryData(nPos) == ULONG_MAX)
319 0 : nPos++;
320 :
321 0 : sal_uLong nSysNumFmt = pFormatter->GetFormatIndex( NF_NUMBER_SYSTEM, eCurLanguage);
322 0 : sal_uLong nSysShortDateFmt = pFormatter->GetFormatIndex( NF_DATE_SYSTEM_SHORT, eCurLanguage);
323 0 : sal_uLong nSysLongDateFmt = pFormatter->GetFormatIndex( NF_DATE_SYSTEM_LONG, eCurLanguage);
324 0 : bool bSysLang = false;
325 0 : if( eCurLanguage == GetAppLanguage() )
326 0 : bSysLang = true;
327 0 : sal_uLong nNumFormatForLanguage = pFormatter->GetFormatForLanguageIfBuiltIn(nSysNumFmt, LANGUAGE_SYSTEM );
328 0 : sal_uLong nShortDateFormatForLanguage = pFormatter->GetFormatForLanguageIfBuiltIn(nSysShortDateFmt, LANGUAGE_SYSTEM );
329 0 : sal_uLong nLongDateFormatForLanguage = pFormatter->GetFormatForLanguageIfBuiltIn(nSysLongDateFmt, LANGUAGE_SYSTEM );
330 :
331 0 : if (
332 0 : nDefFmt == nSysNumFmt ||
333 0 : nDefFmt == nSysShortDateFmt ||
334 0 : nDefFmt == nSysLongDateFmt ||
335 : (
336 0 : bSysLang &&
337 : (
338 0 : nDefFmt == nNumFormatForLanguage ||
339 0 : nDefFmt == nShortDateFormatForLanguage ||
340 : nDefFmt == nLongDateFormatForLanguage
341 : )
342 : )
343 : )
344 : {
345 0 : sValue += SW_RES(RID_STR_SYSTEM);
346 : }
347 :
348 0 : nPos = InsertEntry(sValue, nPos); // Insert as first numeric entry
349 0 : SetEntryData(nPos, (void*)nDefFmt);
350 0 : SelectEntryPos(nPos);
351 0 : nDefFormat = GetFormat();
352 : }
353 :
354 0 : sal_uLong NumFormatListBox::GetFormat() const
355 : {
356 0 : sal_Int32 nPos = GetSelectEntryPos();
357 :
358 0 : return (sal_uLong)GetEntryData(nPos);
359 : }
360 :
361 0 : IMPL_LINK( NumFormatListBox, SelectHdl, ListBox *, pBox )
362 : {
363 0 : sal_uInt16 nPos = pBox->GetSelectEntryPos();
364 0 : OUString sDefine(SW_RES( STR_DEFINE_NUMBERFORMAT ));
365 0 : SwView *pView = GetView();
366 :
367 0 : if( pView && nPos == pBox->GetEntryCount() - 1 &&
368 0 : pBox->GetEntry( nPos ) == sDefine )
369 : {
370 0 : SwWrtShell &rSh = pView->GetWrtShell();
371 0 : SvNumberFormatter* pFormatter = rSh.GetNumberFormatter();
372 :
373 0 : SfxItemSet aCoreSet( rSh.GetAttrPool(),
374 : SID_ATTR_NUMBERFORMAT_VALUE, SID_ATTR_NUMBERFORMAT_VALUE,
375 : SID_ATTR_NUMBERFORMAT_INFO, SID_ATTR_NUMBERFORMAT_INFO,
376 : SID_ATTR_NUMBERFORMAT_ONE_AREA, SID_ATTR_NUMBERFORMAT_ONE_AREA,
377 : SID_ATTR_NUMBERFORMAT_NOLANGUAGE, SID_ATTR_NUMBERFORMAT_NOLANGUAGE,
378 : SID_ATTR_NUMBERFORMAT_ADD_AUTO, SID_ATTR_NUMBERFORMAT_ADD_AUTO,
379 0 : 0 );
380 :
381 0 : double fValue = GetDefValue( nCurrFormatType);
382 :
383 0 : sal_uLong nFormat = pFormatter->GetStandardFormat( nCurrFormatType, eCurLanguage);
384 0 : aCoreSet.Put( SfxUInt32Item( SID_ATTR_NUMBERFORMAT_VALUE, nFormat ));
385 :
386 : aCoreSet.Put( SvxNumberInfoItem( pFormatter, fValue,
387 0 : SID_ATTR_NUMBERFORMAT_INFO ) );
388 :
389 0 : if( (NUMBERFORMAT_DATE | NUMBERFORMAT_TIME) & nCurrFormatType )
390 0 : aCoreSet.Put(SfxBoolItem(SID_ATTR_NUMBERFORMAT_ONE_AREA, bOneArea));
391 :
392 0 : aCoreSet.Put(SfxBoolItem(SID_ATTR_NUMBERFORMAT_NOLANGUAGE, !bShowLanguageControl));
393 0 : aCoreSet.Put(SfxBoolItem(SID_ATTR_NUMBERFORMAT_ADD_AUTO, bUseAutomaticLanguage));
394 :
395 0 : SwAbstractDialogFactory* pFact = SwAbstractDialogFactory::Create();
396 : OSL_ENSURE(pFact, "SwAbstractDialogFactory fail!");
397 :
398 : SfxAbstractDialog* pDlg = pFact->CreateSfxDialog( this, aCoreSet,
399 0 : GetView()->GetViewFrame()->GetFrame().GetFrameInterface(),
400 0 : RC_DLG_SWNUMFMTDLG );
401 : OSL_ENSURE(pDlg, "Dialogdiet fail!");
402 :
403 0 : if (RET_OK == pDlg->Execute())
404 : {
405 0 : const SfxPoolItem* pItem = pView->GetDocShell()->
406 0 : GetItem( SID_ATTR_NUMBERFORMAT_INFO );
407 :
408 0 : if( pItem && 0 != ((SvxNumberInfoItem*)pItem)->GetDelCount() )
409 : {
410 0 : const sal_uInt32* pDelArr = ((SvxNumberInfoItem*)pItem)->GetDelArray();
411 :
412 0 : for ( sal_uInt16 i = 0; i < ((SvxNumberInfoItem*)pItem)->GetDelCount(); i++ )
413 0 : pFormatter->DeleteEntry( pDelArr[i] );
414 : }
415 :
416 0 : const SfxItemSet* pOutSet = pDlg->GetOutputItemSet();
417 0 : if( SFX_ITEM_SET == pOutSet->GetItemState(
418 0 : SID_ATTR_NUMBERFORMAT_VALUE, false, &pItem ))
419 : {
420 0 : sal_uInt32 nNumberFormat = ((SfxUInt32Item*)pItem)->GetValue();
421 : // oj #105473# change order of calls
422 0 : const SvNumberformat* pFmt = pFormatter->GetEntry(nNumberFormat);
423 0 : if( pFmt )
424 0 : eCurLanguage = pFmt->GetLanguage();
425 : // SetDefFormat uses eCurLanguage to look for if this format already in the list
426 0 : SetDefFormat(nNumberFormat);
427 : }
428 0 : if( bShowLanguageControl && SFX_ITEM_SET == pOutSet->GetItemState(
429 0 : SID_ATTR_NUMBERFORMAT_ADD_AUTO, false, &pItem ))
430 : {
431 0 : bUseAutomaticLanguage = ((const SfxBoolItem*)pItem)->GetValue();
432 : }
433 : }
434 : else
435 0 : SetDefFormat(nFormat);
436 :
437 0 : delete pDlg;
438 : }
439 0 : return 0;
440 : }
441 :
442 0 : double NumFormatListBox::GetDefValue(const short nFormatType) const
443 : {
444 0 : double fDefValue = 0.0;
445 :
446 0 : switch (nFormatType)
447 : {
448 : case NUMBERFORMAT_DATE:
449 : case NUMBERFORMAT_DATE|NUMBERFORMAT_TIME:
450 0 : fDefValue = SVX_NUMVAL_DATE;
451 0 : break;
452 :
453 : case NUMBERFORMAT_TIME:
454 0 : fDefValue = SVX_NUMVAL_TIME;
455 0 : break;
456 :
457 : case NUMBERFORMAT_TEXT:
458 : case NUMBERFORMAT_UNDEFINED:
459 0 : fDefValue = 0;
460 0 : break;
461 :
462 : case NUMBERFORMAT_CURRENCY:
463 0 : fDefValue = SVX_NUMVAL_CURRENCY;
464 0 : break;
465 :
466 : case NUMBERFORMAT_PERCENT:
467 0 : fDefValue = SVX_NUMVAL_PERCENT;
468 0 : break;
469 :
470 : case NUMBERFORMAT_LOGICAL:
471 0 : fDefValue = SVX_NUMVAL_BOOLEAN;
472 0 : break;
473 :
474 : default:
475 0 : fDefValue = SVX_NUMVAL_STANDARD;
476 0 : break;
477 : }
478 :
479 0 : return fDefValue;
480 : }
481 :
482 0 : void NumFormatListBox::Clear()
483 : {
484 0 : ListBox::Clear();
485 0 : nCurrFormatType = -1;
486 0 : }
487 :
488 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|