Project

General

Profile

« Previous | Next » 

Revision 4895fff6

Added by Leszek Koltunski over 4 years ago

Beginnings of submitting one's high scores.

View differences:

src/main/java/org/distorted/dialog/RubikDialogNewRecord.java
34 34

  
35 35
import org.distorted.magic.R;
36 36
import org.distorted.magic.RubikActivity;
37
import org.distorted.scores.RubikScoresDownloader;
37
import org.distorted.object.RubikObjectList;
38 38
import org.distorted.uistate.RubikState;
39
import org.distorted.uistate.RubikStatePlay;
39 40

  
40 41
///////////////////////////////////////////////////////////////////////////////////////////////////
41 42

  
......
72 73
      @Override
73 74
      public void onClick(DialogInterface dialog, int which)
74 75
        {
75
        RubikScoresDownloader downloader = RubikScoresDownloader.getInstance();
76
        downloader.submit();
77 76
        RubikActivity act = (RubikActivity)getActivity();
78 77
        RubikState.switchState(act,RubikState.PLAY);
78

  
79
        RubikStatePlay play = (RubikStatePlay) RubikState.PLAY.getStateClass();
80
        int object = play.getObject();
81
        int size   = play.getSize();
82

  
83
        Bundle bundle = new Bundle();
84
        bundle.putInt("tab", RubikObjectList.pack(object,size) );
85
        bundle.putBoolean("submitting", true);
86

  
87
        RubikDialogScores scores = new RubikDialogScores();
88
        scores.setArguments(bundle);
89
        scores.show(act.getSupportFragmentManager(), null);
79 90
        }
80 91
      });
81 92
    builder.setNegativeButton(R.string.no, new DialogInterface.OnClickListener()
src/main/java/org/distorted/dialog/RubikDialogScores.java
83 83

  
84 84
    Bundle args = getArguments();
85 85
    int curTab;
86
    boolean isSubmitting;
86 87

  
87 88
    try
88 89
      {
89 90
      curTab = args.getInt("tab");
91
      isSubmitting = args.getBoolean("submitting");
90 92
      }
91 93
    catch(Exception e)
92 94
      {
93 95
      curTab = 0;
96
      isSubmitting = false;
94 97
      }
95 98

  
96 99
    LayoutInflater inflater = act.getLayoutInflater();
......
99 102

  
100 103
    ViewPager viewPager = view.findViewById(R.id.viewpager);
101 104
    TabLayout tabLayout = view.findViewById(R.id.sliding_tabs);
102
    mPagerAdapter = new RubikDialogScoresPagerAdapter(act,viewPager);
105
    mPagerAdapter = new RubikDialogScoresPagerAdapter(act,viewPager,isSubmitting);
103 106
    tabLayout.setupWithViewPager(viewPager);
104 107

  
105 108
    viewPager.setCurrentItem(curTab);
src/main/java/org/distorted/dialog/RubikDialogScoresPagerAdapter.java
27 27
import android.view.ViewGroup;
28 28
import android.widget.LinearLayout;
29 29

  
30
import org.distorted.magic.R;
31
import org.distorted.scores.RubikScores;
32 30
import org.distorted.scores.RubikScoresDownloader;
33 31
import org.distorted.object.RubikObjectList;
34 32

  
......
42 40
  private RubikDialogScoresView[] mViews;
43 41
  private ViewPager mViewPager;
44 42
  private int mNumTabs;
43
  private boolean mIsSubmitting;
45 44

  
46 45
///////////////////////////////////////////////////////////////////////////////////////////////////
47 46

  
......
116 115

  
117 116
///////////////////////////////////////////////////////////////////////////////////////////////////
118 117

  
119
  public void exception(final String exce)
118
  public void message(final String mess)
120 119
    {
121 120
    mAct.runOnUiThread(new Runnable()
122 121
      {
......
125 124
        {
126 125
        for(int i=0; i<mNumTabs; i++)
127 126
          {
128
          mViews[i].exception(exce);
127
          mViews[i].message(mess);
129 128
          }
130 129
        }
131 130
      });
......
133 132

  
134 133
///////////////////////////////////////////////////////////////////////////////////////////////////
135 134

  
136
  RubikDialogScoresPagerAdapter(FragmentActivity act, ViewPager viewPager)
135
  RubikDialogScoresPagerAdapter(FragmentActivity act, ViewPager viewPager, boolean isSubmitting)
137 136
    {
138 137
    mAct = act;
139 138
    mNumTabs = RubikObjectList.getTotal();
140 139
    mViews = new RubikDialogScoresView[mNumTabs];
141 140
    mViewPager = viewPager;
141
    mIsSubmitting = isSubmitting;
142 142

  
143 143
    viewPager.setAdapter(this);
144 144
    viewPager.setOffscreenPageLimit(mNumTabs-1);
......
150 150
  @NonNull
151 151
  public Object instantiateItem(@NonNull ViewGroup collection, int position)
152 152
    {
153
    mViews[position] = new RubikDialogScoresView(mAct);
153
    mViews[position] = new RubikDialogScoresView(mAct, mIsSubmitting);
154 154
    collection.addView(mViews[position]);
155 155

  
156 156
    boolean allCreated = true;
......
166 166

  
167 167
    if( allCreated )
168 168
      {
169
      RubikScores scores = RubikScores.getInstance();
170 169
      RubikScoresDownloader downloader = RubikScoresDownloader.getInstance();
171
      downloader.download( this, scores.getName(), mAct.getString(R.string.app_version), scores.getNumRuns() );
170

  
171
      if( mIsSubmitting )  downloader.submit  ( this, mAct );
172
      else                 downloader.download( this, mAct );
172 173
      }
173 174

  
174 175
    return mViews[position];
src/main/java/org/distorted/dialog/RubikDialogScoresView.java
57 57

  
58 58
///////////////////////////////////////////////////////////////////////////////////////////////////
59 59

  
60
  public RubikDialogScoresView(Context context)
60
  public RubikDialogScoresView(Context context, boolean isSubmitting)
61 61
    {
62 62
    super(context);
63 63

  
64 64
    View view = inflate(context, R.layout.dialog_scores_downloading, null);
65 65
    addView(view);
66
    TextView text = findViewById(R.id.message_text);
67
    text.setText( context.getString(isSubmitting ? R.string.submitting : R.string.downloading) );
66 68
    }
67 69

  
68 70
///////////////////////////////////////////////////////////////////////////////////////////////////
......
163 165
///////////////////////////////////////////////////////////////////////////////////////////////////
164 166
// needs to run on UI thread
165 167

  
166
  void exception(final String exce)
168
  void message(final String mess)
167 169
    {
168
    TextView text = findViewById(R.id.downloading_text);
169
    text.setText(exce);
170
    TextView text = findViewById(R.id.message_text);
171
    text.setText(mess);
170 172
    }
171 173
  }
src/main/java/org/distorted/magic/RubikActivity.java
210 210

  
211 211
      Bundle bundle = new Bundle();
212 212
      bundle.putInt("tab", RubikObjectList.pack(object,size) );
213
      bundle.putBoolean("submitting", false);
213 214

  
214 215
      RubikDialogScores scores = new RubikDialogScores();
215 216
      scores.setArguments(bundle);
src/main/java/org/distorted/scores/RubikScores.java
73 73
    mDeviceID= -1;
74 74
    }
75 75

  
76
///////////////////////////////////////////////////////////////////////////////////////////////////
77
/*
78
  private static int computeHash()
79
    {
80
    final int MODULO = 227;
81
    int ret = 0;
82

  
83
    for(int i=0; i<MAX_CUBE-1; i++)
84
      ret += (2*i+3)*passedlevel[i];
85

  
86
    for(int i=0; i<MAX_CUBE-1; i++)
87
      for(int j=0; j<MAX_LEVELS; j++)
88
        ret += (i*i+3*j)*records[i][j];
89

  
90
    int length = veriname==null ? 0 : veriname.length();
91

  
92
    for(int i=0;i<length;i++)
93
      ret += i*veriname.charAt(i);
94

  
95
    return (ret%=MODULO);
96
    }
97
*/
98 76
///////////////////////////////////////////////////////////////////////////////////////////////////
99 77

  
100 78
  public static RubikScores getInstance()
......
258 236
///////////////////////////////////////////////////////////////////////////////////////////////////
259 237
// TODO
260 238

  
261
  public void verifyName()
239
  public void successfulSubmit()
262 240
    {
263 241
    mNameIsVerified = true;
264
    }
265

  
266
///////////////////////////////////////////////////////////////////////////////////////////////////
267
// TODO
268 242

  
269
  public void setSubmitted(int object, int size, int scramble)
270
    {
271
    int maxsize = RubikObjectList.getObject(object).getSizes().length;
272

  
273
    if( object>=0 && object<NUM_OBJECTS && size>=0 && size<maxsize && scramble>=1 && scramble<=MAX_SCRAMBLE )
274
      {
275
      mSubmitted[object][size][scramble] = 1;
276
      }
243
    for(int i=0; i<NUM_OBJECTS; i++)
244
      for(int j=0; j<MAX_SIZE   ; j++)
245
        for(int k=0; k<MAX_SCRAMBLE; k++)
246
          {
247
          mSubmitted[i][j][k]=1;
248
          }
277 249
    }
278 250

  
279 251
///////////////////////////////////////////////////////////////////////////////////////////////////
......
301 273

  
302 274
///////////////////////////////////////////////////////////////////////////////////////////////////
303 275

  
304
  private int getDeviceID()
276
  int getDeviceID()
305 277
    {
306 278
    int id;
307 279

  
......
319 291
    return id<0 ? -id : id;
320 292
    }
321 293

  
322

  
323 294
///////////////////////////////////////////////////////////////////////////////////////////////////
324 295

  
325 296
  public long getRecord(int object, int size, int scramble)
......
349 320
    }
350 321

  
351 322
///////////////////////////////////////////////////////////////////////////////////////////////////
352
// TODO
353 323

  
354
  public boolean isVerified()
324
  boolean isVerified()
355 325
    {
356 326
    return mNameIsVerified;
357 327
    }
358 328

  
359 329
///////////////////////////////////////////////////////////////////////////////////////////////////
360
// TODO
361 330

  
362
  public int getNumPlays()
331
  int getNumPlays()
363 332
    {
364 333
    return mNumPlays;
365 334
    }
366 335

  
367 336
///////////////////////////////////////////////////////////////////////////////////////////////////
368 337

  
369
  public int getNumRuns()
338
  int getNumRuns()
370 339
    {
371 340
    return mNumRuns;
372 341
    }
......
384 353
    {
385 354
    return mCountry;
386 355
    }
356

  
357
///////////////////////////////////////////////////////////////////////////////////////////////////
358

  
359
  private String getUnsubmittedList(int mode)
360
    {
361
    RubikObjectList list;
362
    StringBuilder builder = new StringBuilder();
363
    boolean first = true;
364
    int[] sizes;
365
    int length;
366

  
367
    for(int object=0; object<NUM_OBJECTS; object++)
368
      {
369
      list = RubikObjectList.getObject(object);
370
      sizes = list.getSizes();
371
      length = sizes.length;
372

  
373
      for(int size=0; size<length; size++)
374
        {
375
        for(int scramble=0; scramble<MAX_SCRAMBLE; scramble++)
376
          {
377
          if( mSubmitted[object][size][scramble]==0 && mRecords[object][size][scramble]<NO_RECORD )
378
            {
379
            if( !first ) builder.append(',');
380
            else         first=false;
381

  
382
            switch(mode)
383
              {
384
              case 0: builder.append(list.name());
385
                      builder.append("_");
386
                      builder.append(sizes[size]);
387
                      break;
388
              case 1: builder.append(scramble);
389
                      break;
390
              case 2: builder.append(mRecords[object][size][scramble]);
391
                      break;
392
              }
393
            }
394
          }
395
        }
396
      }
397

  
398
    return builder.toString();
399
    }
400

  
401
///////////////////////////////////////////////////////////////////////////////////////////////////
402

  
403
  String getUnsubmittedObjlist()
404
    {
405
    return getUnsubmittedList(0);
406
    }
407

  
408
///////////////////////////////////////////////////////////////////////////////////////////////////
409

  
410
  String getUnsubmittedLevellist()
411
    {
412
    return getUnsubmittedList(1);
413
    }
414

  
415
///////////////////////////////////////////////////////////////////////////////////////////////////
416

  
417
  String getUnsubmittedTimelist()
418
    {
419
    return getUnsubmittedList(2);
420
    }
387 421
  }
src/main/java/org/distorted/scores/RubikScoresDownloader.java
19 19

  
20 20
package org.distorted.scores;
21 21

  
22
import android.support.v4.app.FragmentActivity;
23

  
24
import org.distorted.magic.R;
22 25
import org.distorted.object.RubikObjectList;
23 26

  
24 27
import java.io.InputStream;
......
35 38
  public interface Receiver
36 39
    {
37 40
    void receive(String[][][] country, String[][][] name, float[][][] time);
38
    void exception(String exception);
41
    void message(String mess);
39 42
    }
40 43

  
41 44
  public static final int MAX_PLACES = 10;
......
82 85
  private static boolean mRunning = false;
83 86
  private static int mMode = IDLE;
84 87
  private static Receiver mReceiver;
85
  private static String mUserName, mVersion;
86
  private static int mNumRuns;
88
  private static String mVersion;
87 89

  
88 90
  private static int mTotal = RubikObjectList.getTotal();
89 91
  private static String mScores = "";
......
94 96
  private static int[][] mPlaces = new int[mTotal][MAX_SCRAMBLE];
95 97
  private static RubikScoresDownloader mThis;
96 98

  
99
///////////////////////////////////////////////////////////////////////////////////////////////////
100
// TODO
101

  
102
  private static int computeHash(String name, String veri, String country, String lvllist,
103
                                 String objlist, String timelist, int runnings)
104
    {
105
    return 0;
106
    }
107

  
108
///////////////////////////////////////////////////////////////////////////////////////////////////
109
// TODO: handle the fact that the server might return 'error' (3) or 'name taken' (2)
110

  
111
  private void fillSubmittedValues()
112
    {
113
    fillDownloadedValues();
114
    }
115

  
97 116
///////////////////////////////////////////////////////////////////////////////////////////////////
98 117

  
99
  private void fillValues()
118
  private void fillDownloadedValues()
100 119
    {
101 120
    int begin=-1 ,end, len = mScores.length();
102 121

  
......
197 216

  
198 217
///////////////////////////////////////////////////////////////////////////////////////////////////
199 218

  
200
  private boolean doDownload()
219
  private boolean network(String url)
201 220
    {
202
    String message="https://distorted.org/magic/cgi-bin/download.cgi";
203
    message += "?n="+URLencode(mUserName)+"&r="+mNumRuns+"&e="+mVersion+"d";
204
    message += "&o="+RubikObjectList.getObjectList()+"&min=0&max="+MAX_SCRAMBLE+"&l="+MAX_PLACES;
221
    android.util.Log.e("down", "url: "+url);
205 222

  
206 223
    try
207 224
      {
208
      java.net.URL connectURL = new URL(message);
225
      java.net.URL connectURL = new URL(url);
209 226
      HttpURLConnection conn = (HttpURLConnection)connectURL.openConnection();
210 227

  
211 228
      conn.setDoInput(true);
......
227 244
        }
228 245
      catch( final Exception e)
229 246
        {
230
        mReceiver.exception("Failed to get an answer from the High Scores server");
247
        mReceiver.message("Failed to get an answer from the High Scores server");
231 248
        return false;
232 249
        }
233 250
      }
234 251
    catch( final UnknownHostException e )
235 252
      {
236
      mReceiver.exception("No access to Internet");
253
      mReceiver.message("No access to Internet");
237 254
      return false;
238 255
      }
239 256
    catch( final SecurityException e )
240 257
      {
241
      mReceiver.exception("Application not authorized to connect to the Internet");
258
      mReceiver.message("Application not authorized to connect to the Internet");
242 259
      return false;
243 260
      }
244 261
    catch( final Exception e )
245 262
      {
246
      mReceiver.exception(e.getMessage());
263
      mReceiver.message(e.getMessage());
247 264
      return false;
248 265
      }
249 266

  
250 267
    if( mScores.length()==0 )
251 268
      {
252
      mReceiver.exception("Failed to download scores");
269
      mReceiver.message("Failed to download scores");
253 270
      return false;
254 271
      }
255 272

  
......
270 287
    {
271 288
    boolean success=true;
272 289

  
273
    try
290
    if( mMode==DOWNLOAD && gottaDownload() )
274 291
      {
275
      if( gottaDownload() )
292
      mRunning = true;
293

  
294
      try
276 295
        {
277
        mRunning = true;
278
        success = doDownload();
296
        RubikScores scores = RubikScores.getInstance();
297
        String name = URLencode(scores.getName());
298
        String veri = scores.isVerified() ? name : "";
299
        int numRuns = scores.getNumRuns();
300
        int numPlay = scores.getNumPlays();
301

  
302
        String url="https://distorted.org/magic/cgi-bin/download.cgi";
303
        url += "?n="+name+"&v="+veri+"&r="+numRuns+"&p="+numPlay+"&e="+mVersion+"d";
304
        url += "&o="+RubikObjectList.getObjectList()+"&min=0&max="+MAX_SCRAMBLE+"&l="+MAX_PLACES;
305

  
306
        success = network(url);
279 307
        }
308
      catch( Exception e )
309
        {
310
        mReceiver.message("Exception downloading records: "+e.getMessage() );
311
        }
312

  
313
      fillDownloadedValues();
280 314
      }
281
    catch( Exception e )
315

  
316
    if( mMode==SUBMIT )
282 317
      {
283
      mReceiver.exception("Exception downloading records: "+e.getMessage() );
284
      }
318
      mRunning = true;
285 319

  
286
    fillValues();
320
      try
321
        {
322
        RubikScores scores = RubikScores.getInstance();
323
        String name = URLencode(scores.getName());
324
        String veri = scores.isVerified() ? name : "";
325
        int numRuns = scores.getNumRuns();
326
        int numPlay = scores.getNumPlays();
327
        int deviceID= scores.getDeviceID();
328
        String objlist = scores.getUnsubmittedObjlist();
329
        String lvllist = scores.getUnsubmittedLevellist();
330
        String timlist = scores.getUnsubmittedTimelist();
331
        String country = scores.getCountry();
332
        int hash = computeHash(name,veri,country,lvllist,objlist,timlist,numRuns);
333

  
334
        String url="https://distorted.org/magic/cgi-bin/submit.cgi";
335
        url += "?n="+name+"&v="+veri+"&r="+numRuns+"&p="+numPlay+"&i="+deviceID+"&e="+mVersion+"d";
336
        url += "&o="+objlist+"&l="+lvllist+"&t="+timlist+"&c="+country+"&h="+hash;
337
        url += "&oo="+RubikObjectList.getObjectList()+"&min=0&max="+MAX_SCRAMBLE+"&lo="+MAX_PLACES;
338

  
339
        success = network(url);
340
        }
341
      catch( Exception e )
342
        {
343
        mReceiver.message("Exception submitting records: "+e.getMessage() );
344
        }
345

  
346
      fillSubmittedValues();
347
      }
287 348

  
288 349
    mRunning = false;
289 350

  
......
323 384

  
324 385
///////////////////////////////////////////////////////////////////////////////////////////////////
325 386

  
326
  public void download(Receiver receiver, String userName, String version, int numRuns)
387
  public void download(Receiver receiver, FragmentActivity act)
327 388
    {
328 389
    mReceiver = receiver;
329 390
    mMode     = DOWNLOAD;
330
    mUserName = userName;
331
    mVersion  = version;
332
    mNumRuns  = numRuns;
391
    mVersion  = act.getString(R.string.app_version);
333 392

  
334 393
    Thread networkThrd = new Thread(this);
335 394
    networkThrd.start();
......
337 396

  
338 397
///////////////////////////////////////////////////////////////////////////////////////////////////
339 398

  
340
  public void submit()
399
  public void submit(Receiver receiver, FragmentActivity act)
341 400
    {
342
    mMode = SUBMIT;
401
    mReceiver = receiver;
402
    mMode     = SUBMIT;
403
    mVersion  = act.getString(R.string.app_version);
343 404

  
344
    android.util.Log.e("downloader", "submitting!");
405
    Thread networkThrd = new Thread(this);
406
    networkThrd.start();
345 407
    }
346 408
}
src/main/res/layout/dialog_scores_downloading.xml
1 1
<?xml version="1.0" encoding="utf-8"?>
2 2
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
3
  android:id="@+id/downloading_text"
3
  android:id="@+id/message_text"
4 4
  android:layout_width="match_parent"
5 5
  android:layout_height="match_parent"
6 6
  android:textSize="32sp"
7 7
  android:gravity="center"
8
  android:text="@string/downloading"
9 8
  android:padding="10dp"/>
src/main/res/values/strings.xml
25 25
    <string name="duration">Duration:</string>
26 26
    <string name="type">Type:</string>
27 27
    <string name="downloading">Downloading…</string>
28
    <string name="submitting">Submitting…</string>
28 29
    <string name="credits1">Open Source app developed using the Distorted graphics library. </string>
29 30
    <string name="credits2">Code, tutorials, learn how to write your own graphics effect: <a href="https://distorted.org/redmine/projects/magic-cube/wiki">Distorted.org</a></string>
30 31

  

Also available in: Unified diff