Quelles sont les meilleures pratiques pour utiliser les icônes SVG sur Android?

je suis sur le point de créer mon premier Android natif (donc pas basé sur le navigateur) application et à la recherche de bonnes pratiques concernant la création/provision d'icône. Comme il devrait prendre en charge plusieurs périphériques/résolutions, J'ai pensé qu'il était préférable d'utiliser SVG pour les créer. Il y a au moins ce lib: http://code.google.com/p/svg-android / qui promet d'offrir un support pour SVG sur Android.

Jusqu'à présent, je n'ai pas trouvé de ressources décrire l'utilisation de cette bibliothèque ou d'une autre comme moyen de rendre des icônes SVG sur l'appareil, donc je suis un peu réticent à l'utiliser. Le mieux que j'ai vu jusqu'à présent est D'utiliser SVG comme format source pour le pré-rendu des icônes basées png dans différentes résolutions.

donc mes questions sont les suivantes: les icônes SVG sont-elles une bonne option à utiliser directement sur l'appareil sans étape de pré-rendu png (cela fonctionne-t-il du tout), et si, Pourquoi personne ne semble utiliser cette approche?

66
demandé sur user462982 2012-03-10 19:50:42

12 réponses

pour Android plus ancien que Lollipop, votre meilleure pratique pour SVG sur Android va être d'utiliser un outil pour convertir votre SVG en PNG à la taille(s) que vous êtes intéressé par. Le support SVG existant pour Android n'est pas complet de ce que vous êtes susceptible de trouver dans un fichier SVG, et même si c'était le cas, le support n'est pas intégré dans le système D'exploitation, donc les utiliser directement pour les icônes est certainement hors de question.

commençant par Lollipop (API 21) voir quelles sont les meilleures pratiques d'utilisation Icônes SVG sur Android? . Merci à @MarkWhitaker @AustynMahoney d'avoir souligné cela.

25
répondu mah 2017-05-23 12:02:39

à partir de Lollipop (API 21), Android définit la classe VectorDrawable , pour définir des tirages basés sur des graphiques vectoriels. Android Studio 1.4 ajoute le "Vector Asset Studio" pour les rendre plus faciles à utiliser, y compris une fonction D'importation SVG et un nouveau plugin Gradle qui génère des versions PNG d'icônes Vectorrawable au moment de la construction pour API 20 et plus tôt. Il y a aussi un outil tiers pour conversion des SVG en VectorDrawables . Gardez à l'esprit que bien que les tirables vectoriels puissent être définis en XML, le format de fichier n'est pas SVG et tous les fichiers SVG ne peuvent pas être convertis avec succès. Des graphiques simples comme des icônes devraient fonctionner correctement.

si vous avez encore besoin de générer des PNG vous-même, vous aurez besoin de générer vos icônes à différentes résolutions . Pour la facilité de générer ces icônes de conception PNGs comme SVG et ensuite exporter vers les différentes tailles en utilisant Inkscape qui est libre et plate-forme. Il a quelques belles fonctionnalités pour la conception d'icônes, y compris la vue de prévisualisation D'icône (Voir ci-dessous), et il génère de belles PNG crisp.

enter image description here

39
répondu Mark Whitaker 2016-01-14 10:42:27

c'est Ce que nous utilisons pour transformer un fichier SVG en plusieurs résolutions. Par exemple, pour générer l'icône de lancement: svg2png -w48 icon.svg

#!/bin/bash -e
# Transforms a SVG into a PNG for each platform
# Sizes extracted from
# http://developer.android.com/design/style/iconography.html

[ -z  ] && echo -e "ERROR: filename and one dimension (-w or -h) is required, for example:\nsvg2png -w48 icon.svg\n" && exit 1;
FILENAME=
DEST_FILENAME=`echo  | sed s/\.svg/\.png/`
FLAG=`echo  | cut -c1-2`
ORIGINAL_VALUE=`echo  | cut -c3-`

if [ "$FLAG" != "-w" ] && [ "$FLAG" != "-h" ]; then
    echo "Unknown parameter: $FLAG" 
    exit 1
fi

# PARAMETERS: {multiplier} {destination folder}
function export {
  VALUE=$(echo "scale=0; $ORIGINAL_VALUE*" | bc -l)
  CMD="inkscape $FLAG$VALUE --export-background-opacity=0 --export-png=src/main/res//$DEST_FILENAME src/main/svg/$FILENAME > /dev/null"
  echo $CMD
  eval $CMD
} 

export 1 drawable-mdpi
export 1.5 drawable-hdpi
export 2 drawable-xhdpi
export 3 drawable-xxhdpi
export 4 drawable-xxxhdpi
31
répondu Nacho Coloma 2014-04-11 14:27:33

bonne nouvelle à tous! Depuis le soutien android bibliothèque 23.2 nous pouvons utiliser svg-s till retour à niveau API 7 !

si vous voulez être compatible à l'envers seulement jusqu'à ce que Lollipop (API 21) cochez réponse de Mark Whitaker , mais si vous voulez aller plus bas, vous devez ajouter ces lignes à votre construction.Grad le:

// Gradle Plugin 2.0+ (if you using older version check the library announcement link)
android {  
    defaultConfig {  
        vectorDrawables.useSupportLibrary = true  
    }  
}  

gardez également à l'esprit que:

  • au lieu de android:src vous devez utiliser l'attribut app:srcCompat dans ImageViews.
  • vous ne pouvez pas utiliser svg-s dans StateListDrawables ou d'autres drawables xml, créez-les par programmation À la place.
  • vous ne pouvez pas utiliser l'attribut android:background ou la fonction View.setBackgroundResource() , utilisez la fonction View.setBackground() à la place.
  • vous ne pouvez pas utiliser svg-s en cas de Notifications.
15
répondu bendaf 2017-05-23 11:47:15

depuis nacho-coloma la réponse m'a aidé, j'ai pris son excellent script et l'ai rendu légèrement plus facile à utiliser sur une base quotidienne.

d'Abord:

  1. créer un répertoire drawable-svg à côté de votre répertoire res .
  2. placez vos fichiers svg et ce script dans drawable-svg .
  3. rend le script exécutable.
  4. lancez-le. Dans Ubuntu vous pouvez simplement double-cliquer sur elle dans Nautilus et la faire fonctionner dans un terminal.

et plus tard quand vous recevez de nouveaux fichiers svg:

  1. placez les nouveaux fichiers svg dans drawable-svg et exécutez le script à nouveau.

par défaut il fera ce que vous voulez: mettre à L'échelle chaque fichier svg dans les fichiers png et les mettre dans ../res/drawable-mdpi , ../res/drawable-hdpi etc.

le script prend deux paramètres:

  1. Le fichier svg modèle à l'échelle, par défaut: *.svg
  2. le répertoire de base pour put, par défaut ../res/ (c'est-à-dire votre répertoire res avec la configuration mentionnée ci-dessus).

vous pouvez expérimenter en mettant à l'échelle un seul svg en pngs dans le répertoire courant comme ceci:

$ ./svg2png test.svg .

ou simplement traiter toutes les images:

$ ./svg2png

I je suppose que vous pouvez placer le drawable-svg dans le répertoire res, mais je n'ai pas regardé ce qui est enveloppé dans L'APK finale. En outre, mes fichiers svg ont - dans leurs noms, Ce Que Android n'aime pas, et mon script prend soin de renommer les fichiers png à quelque chose de VALIDE sur Android.

J'utilise ImageMagick pour la conversion qui est légèrement plus standard que Inkscape (bien que j'ai aimé l'approche). Les deux méthodes sont incluses dans le script pour référence.

voici le script:

#!/bin/bash

scalesvg ()
{
    svgfile=""
    pngdir=""
    pngscale=""
    qualifier=""

    svgwidthxheight=$(identify "$svgfile" | cut -d ' ' -f 3)
    svgwidth=${svgwidthxheight%x*}
    svgheight=${svgwidthxheight#*x}

    pngfile="$(basename $svgfile)" # Strip path.
    pngfile="${pngfile/.svg/.png}" # Replace extension.
    pngfile="${pngfile/[^A-Za-z0-9._]/_}" # Replace invalid characters.
    pngfile="$pngdir/$qualifier/$pngfile" # Prepend output path.

    if [ ! -d $(dirname "$pngfile") ]; then
        echo "WARNING: Output directory does not exist: $(dirname "$pngfile")"
        #echo "Exiting"
        #exit 1
        echo "Outputting here instead: $pngfile"
        pngfile="$qualifier-${svgfile/.svg/.png}"
    fi

    pngwidth=$(echo "scale=0; $svgwidth*$pngscale" | bc -l)
    pngheight=$(echo "scale=0; $svgheight*$pngscale" | bc -l)
    pngdensity=$(echo "scale=0; 72*$pngscale" | bc -l) # 72 is default, 

    echo "$svgfile ${svgwidth}×${svgheight}px -> $pngfile ${pngwidth}×${pngheight}px @ $pngdensity dpi"

    convert -background transparent -density $pngdensity "$svgfile" "$pngfile"
    #inkscape -w${pngwidth} --export-background-opacity=0 --export-png="$pngfile" "$svgfile" > /dev/null
    #convert "$svgfile" -background transparent -scale ${pngwidth}x${pngheight} "$pngfile"
}



svgfiles=""
svgfiles="${svgfiles:=*.svg}" # Default to input all *.svg in current dir.

pngdir=""
pngdir="${pngdir:=../res}" # Default to place output pngs to ../res, ie. ../res/drawable-hdpi etc.

for svgfile in $svgfiles; do
    echo "Scaling $svgfile ..."
    scalesvg "$svgfile" "$pngdir" 0.75 drawable-ldpi
    scalesvg "$svgfile" "$pngdir" 1    drawable-mdpi
    scalesvg "$svgfile" "$pngdir" 1.5  drawable-hdpi
    scalesvg "$svgfile" "$pngdir" 2    drawable-xhdpi
    scalesvg "$svgfile" "$pngdir" 3    drawable-xxhdpi
    scalesvg "$svgfile" "$pngdir" 4    drawable-xxxhdpi
done

echo -n "Done."
read # I've made it wait for Enter -- convenient when run from Nautilus.
7
répondu Stephan Henningsen 2016-05-11 14:06:15

une autre option consiste à convertir vos actifs SVG en type de police TTF. Incluez la police sur votre application et utilisez-la de cette façon. Cela fait l'astuce pour les formes simples monochromatiques.

il existe plusieurs outils de conversion gratuits.

6
répondu Chepech 2015-12-02 21:13:03

Android Support Library 23.2 Support des Tirables vectoriels et des Tirables vectoriels animés

  1. ajouter vectorDrawables.useSupportLibrary = true à votre construction.dossier gradle.
  2. utilisez app:srcCompat="@drawable/ic_add" au lieu de android:src="..." ou setImageResource() pour votre ImageView

http://android-developers.blogspot.sk/2016/02/android-support-library-232.html

5
répondu lordmegamax 2016-07-27 10:30:59

les icônes SVG ne sont pas une bonne option à utiliser directement sur un appareil si elles doivent être ajustées à de nombreuses tailles différentes, ce qui est généralement la raison pour laquelle vous souhaitez utiliser le format vecteur en premier lieu. Une grande icône ne sera jamais réduite gracieusement parce que, bien, les écrans d'ordinateur sont faits de pixels. Ainsi, les lignes de l'image vectorielle peuvent être alignées "entre les pixels", créant une bordure floue. En outre, les grandes icônes ont besoin de plus de détails que les petites icônes, qui ont besoin de très peu de détails. Détail icône n'a pas l'air bon dans la très petite taille, et une icône simple ne semble pas bon lorsqu'il est mis à l'échelle dans la très grande taille. J'ai récemment lu un excellent article à ce sujet par un concepteur professionnel D'UI: à propos de ces icônes vectorielles .

3
répondu ZeroOne 2012-04-21 21:34:46

je viens de poster un script pour générer toutes les icônes de plate-forme pour les applications PhoneGap qui peuvent être utiles. Encore à ajouter du code pour générer des écrans.

2
répondu Tony O'Hagan 2014-08-28 02:16:52

je viens de commencer à utiliser Victor , une bibliothèque open source de Trello, pour convertir des fichiers SVG en fichiers PNG des différentes résolutions requises pendant le temps de compilation.

PROS

  • vous n'aurez pas à lancer un script ou un outil pour créer divers fichiers PNG chaque fois que vous changez ou ajoutez une icône. (Vous devez activer la reconstruction sur Android Studio lorsque vous avez ajouté un nouveau fichier svg ou renommé un fichier existant)
  • pas de PNG dans votre source, donc il y a moins de désordre.

CONS

  • le seul inconvénient que J'ai vu jusqu'à présent est que Android Studio ne reconnaît pas encore les ressources générées en XML, donc vous obtiendrez quelques avertissements rouges dans vos fichiers XML et vous n'avez pas d'autocomplete pour vos tirages basés SVG. Il construit bien cependant, et ce problème devrait être corrigé dans une future version D'Android Studio.

si vous utilisez SVG généré par http://materialdesignicons.com / assurez-vous de télécharger le fichier en entier ou de le copier depuis L'onglet'SVG File' En choisissant 'View SVG'

2
répondu Ciske Boekelo 2015-07-23 13:07:32

Je n'ai jamais eu beaucoup de chance avec les scripts shell Linux dans Cygwin sous Windows. Voici donc un fichier batch qui fait ce que fait le script bash de Nacho Coloma. Une petite différence, est que ce fichier batch nécessite à la fois une entrée et un nom de fichier de sortie, comme dans "svg2png-W24 input.sortie svg.png".

installe un dossier" svg " dans le répertoire src/main de votre projet et copie vos fichiers SVG et ce fichier batch dans ce dossier, selon les instructions de Stephan. Exécutez le fichier de commandes à partir du svg dossier. Si vous êtes sous Windows 32 bits, vous devrez probablement changer le chemin D'accès à Inkscape pour utiliser "Program Files (x86)".

@echo off
echo Convert an SVG file to a PNG resource file with multiple resolutions.

rem Check the arguments
set temp=%1
set switch=%temp:~0,2%
set pixels=%temp:~2%
if not "%switch%"=="-w" (
if not "%switch%"=="-h" (
echo Error:  Invalid image width or height switch.  Use -w or -h, with target image size in dp appended.
goto :error
))
echo %pixels%| findstr /r /c:"^[1-9][0-9]*$" >nul
if errorlevel 1 (
echo Error:  Invalid numeric image size.  Image size must be a positive integer.
goto :error
)
if "%3"=="" (
echo Error:  Not enough arguments.
goto :error
)
if not "%4"=="" (
echo Error:  Too many arguments.
goto :error
)

call :export %1 %2 %3 mdpi
call :export %1 %2 %3 hdpi
call :export %1 %2 %3 xhdpi
call :export %1 %2 %3 xxhdpi
call :export %1 %2 %3 xxxhdpi
exit /b

:export
rem parameters: <width/height> <input-file> <output-file> <density>

set temp=%1
set switch=%temp:~0,2%
set pixels=%temp:~2%

if %4==mdpi set /a size=%pixels%
if %4==hdpi set /a size=%pixels%*3/2
if %4==xhdpi set /a size=%pixels%*2
if %4==xxhdpi set /a size=%pixels%*3
if %4==xxxhdpi set /a size=%pixels%*4

echo %size% pixels ../res/drawable-%4/%3
"C:\Program Files\Inkscape\inkscape.exe" %switch%%size% --export-background-opacity=0 --export-png=../res/drawable-%4/%3 %2
exit /b

:error
echo Synopsis: svg2png -w^<width-pixels^>^|-h^<height-pixels^> ^<input-file^> ^<output-file^>
echo Example:  svg2png -w24 "wifi white.svg" wifi_connect_24dp.png
exit /b
0
répondu Linda X 2015-10-08 23:22:52

svg est génial. qui veut utiliser svg:

clic droit sur le dessin" nouvel actif/vecteur "choisissez" icône de matériel" pour les icônes par défaut et "locale SVG file" pour votre fichier dans votre disque dur de l'ordinateur et dans" nom de la ressource "Nom de type pour le fichier svg puis cliquez sur" Suivant "bouton et" terminer "

et vous pouvez l'utiliser dans drawable. fillcolor doit être un code dur.

exemple simple

navigation_toggle.XML

<vector xmlns:android="http://schemas.android.com/apk/res/android"
        android:width="24dp"
        android:height="24dp"
        android:viewportWidth="24.0"
        android:viewportHeight="24.0">
    <path
        android:fillColor="#FFFFFF"
        android:pathData="M3,18h18v-2H3v2zm0,-5h18v-2H3v2zm0,-7v2h18V6H3z"/>
</vector>
0
répondu mehrdad khosravi 2016-01-14 17:05:57