MapContainer上的URLImage未在实际设备上显示,并在模拟器

时间:2017-03-08 07:43:22

标签: google-maps codenameone

我的应用程序有一个地图,用户的头像显示在中心,当用户移动地图时,应添加包括照片在内的标记。

在模拟器上,添加了标记,但是一旦我释放指针,图像就会消失,然后只剩下占位符(这就是我所说的闪烁)。在设备上,除了用户的头像外,没有显示任何内容。

Markers with only the placeholder shown (user avatar's icon is further down)

正如您所看到的,图像不会保留在地图上,只有占位符可以。用户图标位于地图的南部,但会显示。

请注意:我没有收到404错误,地图上只有一个听众(见下文):

以下是我触发地图更新的方法:

googleMap.addMapListener((source, zoom, center) -> {
                showReportsOnMap(googleMap, center, theme, currentForm, selectCategoryButton.getWidth());

});

以下是我在地图中添加报告的方法:

public void showReportsOnMap(
        MapContainer currentMap,
        Coord center,
        Resources theme,
        Form f,
        int reportImageWidth) {

    /**
     * Get the map borders (CAUTION : it can be NaN)
     */
    Coord NE = currentMap.getCoordAtPosition(currentMap.getAbsoluteX() + currentMap.getWidth(), currentMap.getAbsoluteY());
    Coord SW = currentMap.getCoordAtPosition(currentMap.getAbsoluteX(), currentMap.getAbsoluteY() + currentMap.getHeight());

    boolean bordersKnownAndValid = false;

    // Checks that the borders does not contain NaN as longitudes and latitudes
    if (!Double.isNaN(NE.getLatitude())
            && !Double.isNaN(NE.getLongitude())
            && !Double.isNaN(SW.getLatitude())
            && !Double.isNaN(SW.getLongitude())) {
        // The borders can be used
        bordersKnownAndValid = true;
    }

    if (bordersKnownAndValid) {
        ArrayList<Report> localReports = (ArrayList<Report>) (Report.getReportsWithinBoundingBounds(NE, SW, selectedCategoryIdToBeShownOnMap).get(1));

        // Revalidate only if we have something new to show
        if (localReports.size() > 0) {
            currentMap.clearMapLayers();
            currentMap.addMarker(ParametresGeneraux.getCurrentUser().getUserIcon(),
                    new Coord(ParametresGeneraux.getCurrentUser().getCurrentUserLocation().getLatitude(),
                            ParametresGeneraux.getCurrentUser().getCurrentUserLocation().getLongitude()),
                    ParametresGeneraux.getCurrentUser().getUserNickname(), "", null);

            Image tempPlaceholder = Image.createImage(
                    reportImageWidth,
                    reportImageWidth,
                    ParametresGeneraux.accentColor);
            Graphics gr = tempPlaceholder.getGraphics();
            gr.setAntiAliased(true);
            gr.setColor(ParametresGeneraux.accentColor);
            gr.fillArc(0, 0, reportImageWidth, reportImageWidth, 0, 360);

            EncodedImage roundPlaceholder = EncodedImage.createFromImage(tempPlaceholder, true);

            // Add the report on the map
            for (Report report : localReports) {
                String photoFilenameInStorage = Report.getFilename(report.getPhotoPath())
                        + ParametresGeneraux.SUFFIX_ON_MAP_IMAGE;
                EncodedImage reportIcon = EncodedImage.createFromImage(URLImage.createToStorage(roundPlaceholder,
                        photoFilenameInStorage,
                        report.getPhotoPath(),
                        ParametresGeneraux.RESIZE_SCALE_WITH_ROUND_MASK
                ),
                        false); // we want transparency png otherwise it shows black edges

                currentMap.addMarker(reportIcon,
                        new Coord(report.getLocation().getLatitude(), report.getLocation().getLongitude()
                        ),
                        report.getCategory().getName(), "",
                        (evt) -> {
                            // Opens the detail form about this report
                            new ReportDetailsForm(theme, report, f.getClass()).show();
                        });
            }

            currentMap.setCameraPosition(new Coord(center.getLatitude(), center.getLongitude()));
            currentMap.zoom(new Coord(center.getLatitude(),
                    center.getLongitude()),
                    ParametresGeneraux.getUserZoomLevelOnMap());

            currentMap.animate();
            //f.forceRevalidate();
        }

    }

}

所以我猜模拟器中的闪烁是设备上发生的一种慢动作,尽管设备没有显示占位符。

如何使标记与图像一起显示?

2017年3月8日编辑

在模拟器上,如果我在使用此代码将标记添加到地图之前显示对话框:

Dialog.show("Photo", report.getAddress(), Dialog.TYPE_INFO, reportIcon, "OK", null);

图标显示在对话框中(参见下面的屏幕截图)

The Dialog shows the image

然后图像出现在地图上而不会再闪烁,如下所示:

Afterwards the image remains on the map

然而,在实际的Android设备上,甚至没有出现Dialog。

最后我不知道为什么Dialog会使标记在模拟器上表现得如预期,但在设备上却没有,所以我有点迷失了!

任何帮助都是宝贵的。

1 个答案:

答案 0 :(得分:1)

问题是,当您将其添加为标记时,URLImage可能尚未完成下载。如果您在URLImage下载完成之前调用EncodedImage.createFromImage(urlImage),那么您将创建urlImage占位符的编码图像。

com.codename1.io.Util类包含许多从URL下载图像的方法。有些是阻塞,有些使用回调。无论哪种方式,您只需确保在将图像添加到地图之前实际下载图像。

注意:通常这不是URLImage的问题 - 例如如果您将其添加到按钮或标签。这只是一个问题,因为MapContainer是原生的,它实际上需要在调用setMarker()时将图像数据传递给本机层。