如何在Android应用中获取设备的官方营销名称(如Galaxy S25 Ultra)
如何在Android应用中获取设备的官方营销名称(如Galaxy S25 Ultra)
兄弟,我太懂你这个痛点了!你试过的那些方法要么拿的是android.os.Build.BRAND这种厂商名(比如Samsung),要么是Build.MODEL给的SM-S938x这种内部型号,甚至用户自定义的设备名可能是“Fred的手机”,完全不是系统设置里「关于手机」→「产品名称」显示的那种官方营销名,比如Galaxy S25 Ultra对吧?我来给你说几个靠谱的实现方案:
核心思路:读取厂商隐藏的系统属性
其实大部分厂商都会把官方营销名存在特定的系统属性里,只是这些属性没暴露在公开API里,得用反射来读取。
首选方案:读取
ro.product.marketname属性
三星、小米、华为等主流厂商基本都会把营销名存在这个属性里,直接反射调用android.os.SystemProperties的get方法就能拿到:private String getOfficialMarketName() { try { // 反射获取隐藏的SystemProperties类 Class<?> systemPropClass = Class.forName("android.os.SystemProperties"); Method getMethod = systemPropClass.getMethod("get", String.class); // 读取ro.product.marketname属性 String marketName = (String) getMethod.invoke(null, "ro.product.marketname"); // 验证是否是有效的营销名(排除p3sxeea这种内部代号) if (marketName != null && !marketName.trim().isEmpty() && !marketName.matches("^[a-z0-9]+$")) { return marketName; } } catch (Exception e) { // 出现异常就跳过,尝试其他方案 e.printStackTrace(); } return null; }兜底方案:尝试其他厂商特定属性
有些小众厂商可能不用ro.product.marketname,这时候可以多试几个备选属性,比如:private String getFallbackMarketName() { // 常见的厂商营销名属性列表 String[] possibleProps = { "ro.product.vendor.marketname", "ro.vendor.product.marketname", "ro.product.fullname", "ro.samsung.display.product_name" // 三星的另一个备选属性 }; for (String prop : possibleProps) { try { Class<?> systemPropClass = Class.forName("android.os.SystemProperties"); Method getMethod = systemPropClass.getMethod("get", String.class); String propValue = (String) getMethod.invoke(null, prop); if (propValue != null && !propValue.trim().isEmpty() && !propValue.matches("^[a-z0-9]+$")) { return propValue; } } catch (Exception e) { // 单个属性读取失败不影响,继续下一个 } } // 所有属性都拿不到的话,用厂商名+内部型号做兜底 return android.os.Build.BRAND + " " + android.os.Build.MODEL; }
最后整合一下
你可以把两个方法结合起来,先调用首选方案,拿不到再用兜底方案:
private String getDeviceMarketingName() { String marketName = getOfficialMarketName(); if (marketName != null) { return marketName; } return getFallbackMarketName(); }
注意事项
- 反射
SystemProperties在Android 11及以上版本依然可以正常读取大部分ro.product.*属性,除非厂商做了特殊限制,大部分主流机型都没问题。 - 验证逻辑里的
!marketName.matches("^[a-z0-9]+$")是为了排除类似p3sxeea这种纯小写字母数字的内部代号,确保返回的是有意义的营销名。
内容来源于stack exchange




