android: Update app-specific/MIME type icons
[LibreOffice.git] / sw / source / filter / ascii / wrtasc.cxx
blob59097fa9aa865707dd5a06dfadae4323570ba679
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
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/.
9 * This file incorporates work covered by the following license notice:
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 .
20 #include <osl/endian.h>
21 #include <tools/stream.hxx>
22 #include <pam.hxx>
23 #include <doc.hxx>
24 #include <ndtxt.hxx>
25 #include <mdiexp.hxx>
26 #include <fmtcntnt.hxx>
27 #include <frmfmt.hxx>
28 #include "wrtasc.hxx"
29 #include <frameformats.hxx>
30 #include <sfx2/docfile.hxx>
31 #include <sfx2/sfxsids.hrc>
32 #include <o3tl/string_view.hxx>
34 #include <strings.hrc>
36 SwASCWriter::SwASCWriter( std::u16string_view rFltNm )
38 SwAsciiOptions aNewOpts;
40 switch( 5 <= rFltNm.size() ? rFltNm[4] : 0 )
42 case 'D':
43 aNewOpts.SetCharSet( RTL_TEXTENCODING_IBM_850 );
44 aNewOpts.SetParaFlags( LINEEND_CRLF );
45 if( 5 < rFltNm.size() )
47 std::u16string_view aFilterNum = rFltNm.substr( 5 );
48 switch( o3tl::toInt32(aFilterNum) )
50 case 437: aNewOpts.SetCharSet( RTL_TEXTENCODING_IBM_437 ); break;
51 case 850: aNewOpts.SetCharSet( RTL_TEXTENCODING_IBM_850 ); break;
52 case 860: aNewOpts.SetCharSet( RTL_TEXTENCODING_IBM_860 ); break;
53 case 861: aNewOpts.SetCharSet( RTL_TEXTENCODING_IBM_861 ); break;
54 case 863: aNewOpts.SetCharSet( RTL_TEXTENCODING_IBM_863 ); break;
55 case 865: aNewOpts.SetCharSet( RTL_TEXTENCODING_IBM_865 ); break;
58 break;
60 case 'A':
61 #ifndef _WIN32
62 aNewOpts.SetCharSet( RTL_TEXTENCODING_MS_1252 );
63 aNewOpts.SetParaFlags( LINEEND_CRLF );
64 #endif
65 break;
67 case 'M':
68 aNewOpts.SetCharSet( RTL_TEXTENCODING_APPLE_ROMAN );
69 aNewOpts.SetParaFlags( LINEEND_CR );
70 break;
72 case 'X':
73 #ifdef _WIN32
74 aNewOpts.SetCharSet( RTL_TEXTENCODING_MS_1252 );
75 aNewOpts.SetParaFlags( LINEEND_LF );
76 #endif
77 break;
79 default:
80 if( rFltNm.size() >= 4 && rFltNm.substr( 4 )==u"_DLG" )
82 // use the options
83 aNewOpts = GetAsciiOptions();
86 SetAsciiOptions( aNewOpts );
89 SwASCWriter::~SwASCWriter() {}
91 ErrCode SwASCWriter::WriteStream()
93 static constexpr OUStringLiteral STR_CR = u"\015";
94 static constexpr OUStringLiteral STR_LF = u"\012";
95 static constexpr OUStringLiteral STR_CRLF = u"\015\012";
96 static constexpr OUStringLiteral STR_BLANK = u" ";
97 bool bIncludeBOM = GetAsciiOptions().GetIncludeBOM();
98 bool bIncludeHidden = GetAsciiOptions().GetIncludeHidden();
100 if( m_bASCII_ParaAsCR ) // If predefined
101 m_sLineEnd = STR_CR;
102 else if( m_bASCII_ParaAsBlank )
103 m_sLineEnd = STR_BLANK;
104 else
105 switch( GetAsciiOptions().GetParaFlags() )
107 case LINEEND_CR: m_sLineEnd = STR_CR; break;
108 case LINEEND_LF: m_sLineEnd = STR_LF; break;
109 case LINEEND_CRLF: m_sLineEnd = STR_CRLF; break;
112 SwNodeOffset nMaxNode = m_pDoc->GetNodes().Count();
114 if( m_bShowProgress )
115 ::StartProgress( STR_STATSTR_W4WWRITE, 0, sal_Int32(nMaxNode), m_pDoc->GetDocShell() );
117 SwPaM* pPam = m_pOrigPam;
119 bool bWriteSttTag = m_bUCS2_WithStartChar &&
120 (RTL_TEXTENCODING_UCS2 == GetAsciiOptions().GetCharSet() ||
121 RTL_TEXTENCODING_UTF8 == GetAsciiOptions().GetCharSet());
123 rtl_TextEncoding eOld = Strm().GetStreamCharSet();
124 Strm().SetStreamCharSet( GetAsciiOptions().GetCharSet() );
126 // Output all areas of the pam into the ASC file
127 do {
128 bool bTstFly = true;
129 while( m_pCurrentPam->GetPoint()->GetNodeIndex() < m_pCurrentPam->GetMark()->GetNodeIndex() ||
130 (m_pCurrentPam->GetPoint()->GetNodeIndex() == m_pCurrentPam->GetMark()->GetNodeIndex() &&
131 m_pCurrentPam->GetPoint()->GetContentIndex() <= m_pCurrentPam->GetMark()->GetContentIndex()) )
133 SwTextNode* pNd = m_pCurrentPam->GetPoint()->GetNode().GetTextNode();
134 if( pNd )
136 // Should we have frames only?
137 // That's possible, if we put a frame selection into the clipboard
138 if( bTstFly && m_bWriteAll &&
139 pNd->GetText().isEmpty() &&
140 // Frame exists
141 !m_pDoc->GetSpzFrameFormats()->empty() &&
142 // Only one node in the array
143 m_pDoc->GetNodes().GetEndOfExtras().GetIndex() + 3 ==
144 m_pDoc->GetNodes().GetEndOfContent().GetIndex() &&
145 // And exactly this one is selected
146 m_pDoc->GetNodes().GetEndOfContent().GetIndex() - 1 ==
147 m_pCurrentPam->GetPoint()->GetNodeIndex() )
149 // Print the frame's content.
150 // It is always at position 0!
151 const SwFrameFormat* pFormat = (*m_pDoc->GetSpzFrameFormats())[ 0 ];
152 const SwNodeIndex* pIdx = pFormat->GetContent().GetContentIdx();
153 if( pIdx )
155 m_pCurrentPam = NewUnoCursor(*m_pDoc, pIdx->GetIndex(),
156 pIdx->GetNode().EndOfSectionIndex() );
157 m_pCurrentPam->Exchange();
158 continue; // reset while loop!
161 else if (!pNd->IsHidden() || bIncludeHidden)
163 if (bWriteSttTag)
165 switch(GetAsciiOptions().GetCharSet())
167 case RTL_TEXTENCODING_UTF8:
168 if( bIncludeBOM )
170 Strm().WriteUChar( 0xEF ).WriteUChar( 0xBB ).WriteUChar( 0xBF );
173 break;
174 case RTL_TEXTENCODING_UCS2:
175 #ifdef OSL_LITENDIAN
176 Strm().SetEndian(SvStreamEndian::LITTLE);
177 #else
178 Strm().SetEndian(SvStreamEndian::BIG);
179 #endif
180 if( bIncludeBOM )
182 Strm().StartWritingUnicodeText();
184 break;
187 bWriteSttTag = false;
189 Out( aASCNodeFnTab, *pNd, *this );
191 bTstFly = false; // Testing once is enough
194 if( !m_pCurrentPam->Move( fnMoveForward, GoInNode ) )
195 break;
197 if( m_bShowProgress )
198 ::SetProgressState( sal_Int32(m_pCurrentPam->GetPoint()->GetNodeIndex()),
199 m_pDoc->GetDocShell() ); // How far?
202 } while( CopyNextPam( &pPam ) ); // Until all pams are processed
204 Strm().SetStreamCharSet( eOld );
206 if( m_bShowProgress )
207 ::EndProgress( m_pDoc->GetDocShell() );
209 return ERRCODE_NONE;
212 void SwASCWriter::SetupFilterOptions(SfxMedium& rMedium)
214 const SfxItemSet* pSet = rMedium.GetItemSet();
215 if( nullptr != pSet )
217 if( const SfxStringItem* pItem = pSet->GetItemIfSet( SID_FILE_FILTEROPTIONS ) )
219 SwAsciiOptions aOpt;
220 OUString sItemOpt;
221 sItemOpt = pItem->GetValue();
222 aOpt.ReadUserData(sItemOpt);
223 SetAsciiOptions(aOpt);
228 void GetASCWriter(
229 std::u16string_view rFltNm, [[maybe_unused]] const OUString& /*rBaseURL*/, WriterRef& xRet )
231 xRet = new SwASCWriter( rFltNm );
234 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */