Skip to content

Commit

Permalink
First pass at a map view for Towers. Still a WIP
Browse files Browse the repository at this point in the history
  • Loading branch information
christianrowlands committed Apr 25, 2024
1 parent 415ec93 commit 6f74aeb
Show file tree
Hide file tree
Showing 12 changed files with 576 additions and 4 deletions.
10 changes: 10 additions & 0 deletions build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,16 @@ allprojects {
google()
mavenCentral()
maven { url 'https://jitpack.io' }
maven {
url 'https://api.mapbox.com/downloads/v2/releases/maven'
authentication {
basic(BasicAuthentication)
}
credentials {
username = "mapbox"
password = MAPBOX_ACCESS_TOKEN
}
}
}
}

Expand Down
12 changes: 10 additions & 2 deletions networksurvey/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,8 @@ android {
compileSdk 34
defaultConfig {
buildConfigField "String", "MESSAGING_API_VERSION", "\"${networkSurveyMessagingVersion}\""
buildConfigField 'String', "MAPBOX_ACCESS_TOKEN", "\"${MAPBOX_ACCESS_TOKEN}\""
buildConfigField 'String', "NS_API_KEY", "\"${NS_API_KEY}\""
applicationId "com.craxiom.networksurvey"
minSdkVersion 26
targetSdkVersion 34
Expand Down Expand Up @@ -121,11 +123,17 @@ dependencies {

implementation 'com.github.yuriy-budiyev:code-scanner:2.1.2'

implementation 'com.mapbox.extension:maps-compose:11.3.0'
implementation 'com.mapbox.maps:android:11.3.0'

implementation 'com.squareup.retrofit2:retrofit:2.9.0'
implementation 'com.squareup.retrofit2:converter-gson:2.9.0'

implementation 'org.projectlombok:lombok:1.18.24'
annotationProcessor 'org.projectlombok:lombok:1.18.24'

// Compose
def composeBom = platform('androidx.compose:compose-bom:2024.02.02')
def composeBom = platform('androidx.compose:compose-bom:2024.04.01')
implementation(composeBom)
androidTestImplementation(composeBom)

Expand All @@ -142,7 +150,7 @@ dependencies {
implementation "com.google.accompanist:accompanist-themeadapter-material:0.28.0"

// Only include firebase in the google play build
regularImplementation platform('com.google.firebase:firebase-bom:32.7.4')
regularImplementation platform('com.google.firebase:firebase-bom:32.8.1')
regularImplementation 'com.google.firebase:firebase-analytics'
regularImplementation 'com.google.firebase:firebase-crashlytics'

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
import android.content.ServiceConnection;
import android.os.IBinder;

import androidx.annotation.CallSuper;
import androidx.fragment.app.Fragment;

import com.craxiom.networksurvey.services.NetworkSurveyService;
Expand Down Expand Up @@ -67,6 +68,7 @@ public void onDestroy()
*
* @param surveyService The service reference to make calls on.
*/
@CallSuper
protected void onSurveyServiceDisconnecting(NetworkSurveyService surveyService)
{
service = null;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,9 @@
import android.location.LocationProvider;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TableLayout;
Expand All @@ -22,9 +25,12 @@
import androidx.annotation.Nullable;
import androidx.appcompat.app.AlertDialog;
import androidx.core.app.ActivityCompat;
import androidx.core.view.MenuProvider;
import androidx.fragment.app.FragmentActivity;
import androidx.lifecycle.LifecycleOwner;
import androidx.lifecycle.ViewModelProvider;
import androidx.lifecycle.ViewModelStoreOwner;
import androidx.navigation.Navigation;
import androidx.navigation.fragment.NavHostFragment;

import com.craxiom.messaging.GsmRecord;
Expand Down Expand Up @@ -52,10 +58,13 @@
import com.craxiom.networksurvey.services.NetworkSurveyService;
import com.craxiom.networksurvey.ui.cellular.CellularChartViewModel;
import com.craxiom.networksurvey.ui.cellular.ComposeFunctions;
import com.craxiom.networksurvey.ui.cellular.model.ServingCellInfo;
import com.craxiom.networksurvey.util.CellularUtils;
import com.craxiom.networksurvey.util.ColorUtils;
import com.craxiom.networksurvey.util.MathUtils;
import com.craxiom.networksurvey.util.ParserUtils;
import com.google.protobuf.Descriptors;
import com.google.protobuf.GeneratedMessageV3;
import com.mackhartley.roundedprogressbar.RoundedProgressBar;

import java.text.DecimalFormat;
Expand All @@ -75,7 +84,7 @@
*
* @since 1.6.0 (It really came earlier, but was minimal until the 1.6.0 rewrite.
*/
public class NetworkDetailsFragment extends AServiceDataFragment implements ICellularSurveyRecordListener, LocationListener
public class NetworkDetailsFragment extends AServiceDataFragment implements ICellularSurveyRecordListener, LocationListener, MenuProvider
{
public static final String SUBSCRIPTION_ID_KEY = "subscription_id";

Expand All @@ -94,6 +103,7 @@ public class NetworkDetailsFragment extends AServiceDataFragment implements ICel
private FragmentNetworkDetailsBinding binding;
private CellularViewModel viewModel;
private CellularChartViewModel chartViewModel;
private CellularRecordWrapper latestServingCellRecord;

@Override
public void onCreate(@Nullable Bundle savedInstanceState)
Expand Down Expand Up @@ -126,6 +136,12 @@ public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup c
chartViewModel.addInitialRssi(UNKNOWN_RSSI);
ComposeFunctions.setContent(binding.composeView, chartViewModel);

FragmentActivity activity = getActivity();
if (activity != null)
{
activity.addMenuProvider(this, getViewLifecycleOwner());
}

return binding.getRoot();
}

Expand Down Expand Up @@ -225,6 +241,35 @@ public void onLocationChanged(@NonNull Location location)
viewModel.setLocation(location);
}

@Override
public void onCreateMenu(@NonNull Menu menu, @NonNull MenuInflater menuInflater)
{
menuInflater.inflate(R.menu.cellular_details_menu, menu);
}

@Override
public boolean onMenuItemSelected(@NonNull MenuItem menuItem)
{
if (menuItem.getItemId() == R.id.action_open_tower_map)
{
navigateToTowerMap();
return true;
}
return false;
}

/**
* Navigates to the cell tower map screen.
*/
public void navigateToTowerMap()
{
FragmentActivity activity = getActivity();
if (activity == null) return;

Navigation.findNavController(activity, R.id.main_content)
.navigate(MainCellularFragmentDirections.actionMainCellularFragmentToTowerMapFragment(new ServingCellInfo(latestServingCellRecord, subscriptionId)));
}

/**
* Initialize the UI listeners for the various buttons and other UI elements.
*/
Expand Down Expand Up @@ -583,6 +628,11 @@ private void processCellularGroup(List<CellularRecordWrapper> cellularGroup)
final List<NrRecordData> nrNeighbors = new ArrayList<>();
for (CellularRecordWrapper cellularRecord : cellularGroup)
{
if (isServingCell(cellularRecord.cellularRecord))
{
latestServingCellRecord = cellularRecord;
}

switch (cellularRecord.cellularProtocol)
{
case NONE:
Expand Down Expand Up @@ -648,6 +698,22 @@ private void processCellularGroup(List<CellularRecordWrapper> cellularGroup)
processNrNeighbors(nrNeighbors);
}

/**
* @return Returns true if the servingCell field is present and also set to true.
*/
private boolean isServingCell(GeneratedMessageV3 message)
{
try
{
Descriptors.Descriptor descriptor = message.getDescriptorForType();
Descriptors.FieldDescriptor field = descriptor.findFieldByName("servingCell");
return (boolean) message.getField(field);
} catch (Exception e)
{
return false;
}
}

/**
* Takes in the GSM serving cell details and sets it in the view model so that it can be
* displayed in the UI.
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,83 @@
package com.craxiom.networksurvey.fragments

import android.os.Bundle
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import androidx.compose.ui.platform.ComposeView
import androidx.compose.ui.platform.ViewCompositionStrategy
import androidx.lifecycle.viewmodel.compose.viewModel
import androidx.navigation.fragment.navArgs
import com.craxiom.networksurvey.listeners.ICellularSurveyRecordListener
import com.craxiom.networksurvey.model.CellularRecordWrapper
import com.craxiom.networksurvey.services.NetworkSurveyService
import com.craxiom.networksurvey.ui.cellular.TowerMapScreen
import com.craxiom.networksurvey.ui.cellular.model.TowerMapViewModel
import com.craxiom.networksurvey.util.NsTheme
import java.util.Collections

/**
* A map view of all the towers in the area as pulled from the NS Tower Service.
*/
class TowerMapFragment : AServiceDataFragment(), ICellularSurveyRecordListener {
private lateinit var viewModel: TowerMapViewModel

override fun onCreateView(
inflater: LayoutInflater,
container: ViewGroup?,
savedInstanceState: Bundle?
): View {
val args: TowerMapFragmentArgs by navArgs()
val servingCell = args.servingCell

val composeView = ComposeView(requireContext())

composeView.apply {
setViewCompositionStrategy(ViewCompositionStrategy.DisposeOnViewTreeLifecycleDestroyed)
setContent {
viewModel = viewModel()

NsTheme {
TowerMapScreen(viewModel = viewModel)
}

onCellularBatch(
Collections.singletonList(servingCell.servingCell),
servingCell.subscriptionId
)
}
}

return composeView
}

override fun onResume() {
super.onResume()

startAndBindToService()
}

override fun onSurveyServiceConnected(service: NetworkSurveyService?) {
if (service == null) return
service.registerCellularSurveyRecordListener(this)
}

override fun onSurveyServiceDisconnecting(service: NetworkSurveyService?) {
if (service == null) return
service.unregisterCellularSurveyRecordListener(this)

super.onSurveyServiceDisconnecting(service)
}

override fun onCellularBatch(
cellularGroup: MutableList<CellularRecordWrapper>?,
subscriptionId: Int
) {
// FIXME FINISH THIS
/*viewModel.onCellularBatchResults(
ServingCellInfo(
cellularGroup?.firstOrNull { it.data.subscriptionId == subscriptionId } ?: return
)
)*/
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ import com.craxiom.networksurvey.util.PreferenceUtils
import com.craxiom.networksurvey.util.WifiUtils

/**
* The fragment that displays the details of a single Wifi network from the scan results.
* The fragment that enables visualizing the the latest scan results on a simple spectrum view.
*/
class WifiSpectrumFragment : AServiceDataFragment(), IWifiSurveyRecordListener {
private lateinit var screenViewModel: WifiSpectrumScreenViewModel
Expand Down
Loading

0 comments on commit 6f74aeb

Please sign in to comment.