ChatGPT解决这个技术问题 Extra ChatGPT

Android XML Percent Symbol

I have an array of strings in which the % symbol is used. Proper format for using the % is %. When I have a string in that array with multiple % it gives me this error.

 Multiple annotations found at this
 line:
 - error: Multiple substitutions specified in non-positional format;
   did you mean to add the formatted="false" attribute?
 - error: Found tag </item> where </string-array> is expected
Can you post the XML that's causing this error? It can be very difficult to identify a problem without seeing it's cause.
this is an error that can easily be replicated by any string with 2 or more % symbols.
If not looking for formatting purpose, better way to accomplish.
In my case, I wrongly entered the formatting param as 1%$s, instead of %1$s.

J
Josef Pfleger

The Android Asset Packaging Tool (aapt) has become very strict in its latest release and is now used for all Android versions. The aapt-error you're getting is generated because it no longer allows non-positional format specifiers.

Here are a few ideas how you can include the %-symbol in your resource strings.

If you don't need any format specifiers or substitutions in your string you can simply make use of the formatted attribute and set it to false:

<string formatted="false">%a + %a == 2%a</string>

In this case the string is not used as a format string for the Formatter so you don't have to escape your %-symbols. The resulting string is "%a + %a == 2%a".

If you omit the formatted="false" attribute, the string is used as a format string and you have to escape the %-symbols. This is correctly done with double-%:

<string>%%a + %%a == 2%%a</string>

Now aapt gives you no errors but depending on how you use it, the resulting string can be "%%a + %%a == 2%%a" if a Formatter is invoked without any format arguments:

Resources res = context.getResources();

String s1 = res.getString(R.string.str);
// s1 == "%%a + %%a == 2%%a"

String s2 = res.getString(R.string.str, null);
// s2 == "%a + %a == 2%a"

Without any xml and code it is difficult to say what exactly your problem is but hopefully this helps you understand the mechanisms a little better.


i selected this as the answer because it should work, but apparently there is a bug that im running into with that string, so ive decided to use %% and "XXX.replaceAll("%%", "%");"
using formatted=false works nicely. This is how I used it: \'Sweet\' 10% to 20% even 35% sugar by weight
formatted=false works nicely for me too. Using %%, it literally showed up as %% on my device and emulator..
formatted=false worked fine for me in the past. now (ADT 22) , for some reason it doesn't. and if i use : " str=mContext.getString(R.string.str,"hello") " , it will have this lint warning: "Format string 'str' is not a valid format string so it should not be passed to String.format"
If you are accessing from , then for printing percentage use \u0025. This worked for me.
P
Paul E.

To allow the app using formatted strings from resources you should correct your xml. So, for example

<string name="app_name">Your App name, ver.%d</string>

should be replaced with

<string name="app_name">Your App name, ver.%1$d</string>

You can see this for details.


Thanks, you provided the missing link - literally.
For multiple parameter substitution (e.g. with strings), use %1$s, %2$s etc.
who will read such a big answer for this little thing? Thanks, I scroll down to find you.
M
Mostafa Arian Nejad

You can escape % using %% for XML parser, but it is shown twice in device.

To show it once, try following format: \%%

For Example

<string name="zone_50">Fat Burning (50\%% to 60\%%)</string> 

is shown as Fat Burning (50% to 60%) in device


\%% causes crashes on Nexus 4 4.2.1. Haven't tested others.
This works well and is easy when you already know the percent you want to include into your strings, versus using string formatter and always having to set those hardcoded values programmatically.
This crashed for me as well on Nexus 5.1.1. @ViliusK answer is the correct one.
just use %% instead of %
V
ViliusK

Use

<string name="win_percentage">%d%% wins</string>

to get

80% wins as a formatted string.

I'm using String.format() method to get the number inserted instead of %d.


l
landerlyoung

to escape the percent symbol, you just need %%

for example :

String.format("%1$d%%", 10)

returns "10%"


Your answer is pretty much the same as several other existing answers
... and wrong, because returns 10% not %10. FIY: When you use String.format you should everytime specify Locale. You can be really surprised when you don't put Locale and use Arabic locale for format numbers...
A
Asaf Pinhassi

In your strings.xml file you can use any Unicode sign you want.

For example, the Unicode number for percent sign is 0025:

<string name="percent_sign">&#x0025;</string>

You can see a comprehensive list of Unicode signs here


That does not make any sense. % and % are identical in a xml file.
The resource file is converted into a Java resource, and in doing so, the % character returns. I'm afraid this doesn't resolve the problem.
G
Garytech

Not exactly your problem but a similar one.

If you have more than one formatting in your string entry, you should not use "%s" multiple times.

DON'T :

<string name="entry">Planned time %s - %s (%s)</string>

DO :

<string name="entry">Planned time %1$s - %2$s (%3$s)</string>

M
Mee

You can escape the % in xml with %%, but you need to set the text in code, not in layout xml.


Yes it does escape with double %, and compile nicely. But when run on emulator, or even devices, it could show up as %%.
B
Bao Le

A tricky method: using small percent sign as below

 <string name="zone_50">Fat Burning (50&#65130; to 60&#65130;)</string> 

Percent Sign on Wikipedia


S
Steve Waring

This could be a case of the IDE becoming too strict.

The idea is sound, in general you should specify the order of substitution variables so that should you add resources for another language, your java code will not need to be changed. However there are two issues with this:

Firstly, a string such as:

You will need %.5G %s

to be used as You will need 2.1200 mg will have the order the same in any language as that amount of mass is always represented in that order scientifically.

The second is that if you put the order of variables in what ever language your default resources are specified in (eg English) then you only need to specify the positions in the resource strings for languages the use a different order to your default language.

The good news is that this is simple to fix. Even though there is no need to specify the positions, and the IDE is being overly strict, just specify them anyway. For the example above use:

You will need %1$.5G %2$s


D
Dave Clemmer

Try this one (right):

<string name="content" formatted="false">Great application %s  ☞  %s  ☞  %s \\n\\nGo to download this application %s</string>

t
techtinkerer

Per google official documentation, use %1$s and %2$s http://developer.android.com/guide/topics/resources/string-resource.html#FormattingAndStyling

Hello, %1$s! You have %2$d new messages.


H
Harish Rana

Suppose you want to show (50% OFF) and enter 50 at runtime. Here is the code:

<string name="format_discount"> (
<xliff:g id="discount">%1$s</xliff:g>
<xliff:g id="percentage_sign">%2$s</xliff:g>
 OFF)</string>

In the java class use this code:

String formattedString=String.format(context.getString(R.string.format_discount),discountString,"%");
holder1.mTextViewDiscount.setText(formattedString);

l
lolraccoon

Try using a backslash in front of it, like below:

\%

This solution leads to crashing .

关注公众号,不定期副业成功案例分享
Follow WeChat

Success story sharing

Want to stay one step ahead of the latest teleworks?

Subscribe Now