Project

General

Profile

« Previous | Next » 

Revision e108b57e

Added by Leszek Koltunski over 4 years ago

Re-add the Pattern dialog, but attach it to the Pattern uistate this time.
The idea to do away with the dialog proves impossible - we'd have to resize the top bar, which causes very unpleasant flashes.

View differences:

src/main/java/org/distorted/dialog/RubikDialogPattern.java
1
///////////////////////////////////////////////////////////////////////////////////////////////////
2
// Copyright 2019 Leszek Koltunski                                                               //
3
//                                                                                               //
4
// This file is part of Magic Cube.                                                              //
5
//                                                                                               //
6
// Magic Cube is free software: you can redistribute it and/or modify                            //
7
// it under the terms of the GNU General Public License as published by                          //
8
// the Free Software Foundation, either version 2 of the License, or                             //
9
// (at your option) any later version.                                                           //
10
//                                                                                               //
11
// Magic Cube is distributed in the hope that it will be useful,                                 //
12
// but WITHOUT ANY WARRANTY; without even the implied warranty of                                //
13
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the                                 //
14
// GNU General Public License for more details.                                                  //
15
//                                                                                               //
16
// You should have received a copy of the GNU General Public License                             //
17
// along with Magic Cube.  If not, see <http://www.gnu.org/licenses/>.                           //
18
///////////////////////////////////////////////////////////////////////////////////////////////////
19

  
20
package org.distorted.dialog;
21

  
22
import android.app.Dialog;
23
import android.content.Context;
24
import android.content.DialogInterface;
25
import android.os.Bundle;
26
import android.support.annotation.NonNull;
27
import android.support.v4.app.FragmentActivity;
28
import android.support.v4.view.ViewPager;
29
import android.support.v7.app.AlertDialog;
30
import android.support.v7.app.AppCompatDialogFragment;
31
import android.support.design.widget.TabLayout;
32
import android.util.DisplayMetrics;
33
import android.view.LayoutInflater;
34
import android.view.View;
35
import android.view.Window;
36
import android.view.WindowManager;
37
import android.widget.ImageView;
38
import android.widget.TextView;
39

  
40
import org.distorted.magic.R;
41
import org.distorted.patterns.RubikPattern;
42

  
43
///////////////////////////////////////////////////////////////////////////////////////////////////
44

  
45
public class RubikDialogPattern extends AppCompatDialogFragment
46
  {
47
  RubikDialogPatternPagerAdapter mPagerAdapter;
48

  
49
///////////////////////////////////////////////////////////////////////////////////////////////////
50

  
51
  @Override
52
  public void onStart()
53
    {
54
    super.onStart();
55

  
56
    Window window = getDialog().getWindow();
57
    window.setFlags(WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL,
58
                    WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL);
59
    window.clearFlags(WindowManager.LayoutParams.FLAG_DIM_BEHIND);
60
    }
61

  
62
///////////////////////////////////////////////////////////////////////////////////////////////////
63

  
64
  @NonNull
65
  @Override
66
  public Dialog onCreateDialog(Bundle savedInstanceState)
67
    {
68
    FragmentActivity act = getActivity();
69
    AlertDialog.Builder builder = new AlertDialog.Builder(act);
70

  
71
    LayoutInflater layoutInflater = act.getLayoutInflater();
72
    TextView tv = (TextView) layoutInflater.inflate(R.layout.dialog_title, null);
73
    tv.setText(R.string.patterns);
74
    builder.setCustomTitle(tv);
75

  
76
    Bundle args = getArguments();
77
    int curTab;
78

  
79
    try
80
      {
81
      curTab = args.getInt("tab");
82
      }
83
    catch(Exception e)
84
      {
85
      curTab = 0;
86
      }
87

  
88
    LayoutInflater inflater = act.getLayoutInflater();
89
    final View view = inflater.inflate(R.layout.dialog_tabbed, null);
90
    builder.setView(view);
91

  
92
    ViewPager viewPager = view.findViewById(R.id.viewpager);
93
    TabLayout tabLayout = view.findViewById(R.id.sliding_tabs);
94
    mPagerAdapter = new RubikDialogPatternPagerAdapter(act, viewPager, this);
95
    tabLayout.setupWithViewPager(viewPager);
96
    viewPager.setCurrentItem(curTab);
97

  
98
    int[] iconID = { R.drawable.cube2, R.drawable.cube3, R.drawable.cube4, R.drawable.cube5 };
99

  
100
    for(int i=0; i< RubikPattern.NUM_CUBES; i++)
101
      {
102
      ImageView imageView = new ImageView(act);
103
      imageView.setImageResource(iconID[i]);
104
      TabLayout.Tab tab = tabLayout.getTabAt(i);
105
      if(tab!=null) tab.setCustomView(imageView);
106
      }
107

  
108
    return builder.create();
109
    }
110

  
111
///////////////////////////////////////////////////////////////////////////////////////////////////
112

  
113
  @Override
114
  public void onResume()
115
    {
116
    super.onResume();
117

  
118
    Window window = getDialog().getWindow();
119
    Context context = getContext();
120

  
121
    if( window!=null && context!=null )
122
      {
123
      DisplayMetrics metrics = context.getResources().getDisplayMetrics();
124
      final float height= metrics.heightPixels;
125

  
126
      WindowManager.LayoutParams params = window.getAttributes();
127
      params.width = WindowManager.LayoutParams.WRAP_CONTENT;
128
      params.height = (int)(0.75f*height);
129
      window.setAttributes(params);
130
      }
131
    }
132

  
133
///////////////////////////////////////////////////////////////////////////////////////////////////
134

  
135
  public static String getDialogTag()
136
    {
137
    return "DialogPattern";
138
    }
139
  }
src/main/java/org/distorted/dialog/RubikDialogPatternPagerAdapter.java
1
///////////////////////////////////////////////////////////////////////////////////////////////////
2
// Copyright 2020 Leszek Koltunski                                                               //
3
//                                                                                               //
4
// This file is part of Magic Cube.                                                              //
5
//                                                                                               //
6
// Magic Cube is free software: you can redistribute it and/or modify                            //
7
// it under the terms of the GNU General Public License as published by                          //
8
// the Free Software Foundation, either version 2 of the License, or                             //
9
// (at your option) any later version.                                                           //
10
//                                                                                               //
11
// Magic Cube is distributed in the hope that it will be useful,                                 //
12
// but WITHOUT ANY WARRANTY; without even the implied warranty of                                //
13
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the                                 //
14
// GNU General Public License for more details.                                                  //
15
//                                                                                               //
16
// You should have received a copy of the GNU General Public License                             //
17
// along with Magic Cube.  If not, see <http://www.gnu.org/licenses/>.                           //
18
///////////////////////////////////////////////////////////////////////////////////////////////////
19

  
20
package org.distorted.dialog;
21

  
22
import android.support.annotation.NonNull;
23
import android.support.v4.app.FragmentActivity;
24
import android.support.v4.view.PagerAdapter;
25
import android.support.v4.view.ViewPager;
26
import android.view.View;
27
import android.view.ViewGroup;
28

  
29
import org.distorted.patterns.RubikPattern;
30

  
31
///////////////////////////////////////////////////////////////////////////////////////////////////
32

  
33
class RubikDialogPatternPagerAdapter extends PagerAdapter
34
  {
35
  private FragmentActivity mAct;
36
  private RubikDialogPatternView[] mViews;
37
  private RubikDialogPattern mDialog;
38
  private int mNumTabs;
39

  
40
///////////////////////////////////////////////////////////////////////////////////////////////////
41

  
42
  private String[] createCategories(int pos)
43
    {
44
    RubikPattern pattern = RubikPattern.getInstance();
45
    int numCat = pattern.getNumCategories(pos);
46

  
47
    String[] ret = new String[numCat];
48

  
49
    for(int i=0; i<numCat; i++)
50
      {
51
      ret[i] = pattern.getCategoryName(pos,i);
52
      }
53

  
54
    return ret;
55
    }
56

  
57
///////////////////////////////////////////////////////////////////////////////////////////////////
58

  
59
  RubikDialogPatternPagerAdapter(FragmentActivity act, ViewPager viewPager, RubikDialogPattern dialog)
60
    {
61
    mAct = act;
62
    mDialog = dialog;
63
    mNumTabs = RubikPattern.NUM_CUBES;
64
    mViews = new RubikDialogPatternView[mNumTabs];
65

  
66
    viewPager.setAdapter(this);
67
    viewPager.setOffscreenPageLimit(mNumTabs-1);
68
    }
69

  
70
///////////////////////////////////////////////////////////////////////////////////////////////////
71

  
72
  @Override
73
  @NonNull
74
  public Object instantiateItem(@NonNull ViewGroup collection, final int position)
75
    {
76
    String[] categories = createCategories(position);
77
    mViews[position] = new RubikDialogPatternView(mAct, mDialog, categories);
78
    collection.addView(mViews[position]);
79

  
80
    return mViews[position];
81
    }
82

  
83
///////////////////////////////////////////////////////////////////////////////////////////////////
84

  
85
  @Override
86
  public void destroyItem(ViewGroup collection, int position, @NonNull Object view)
87
    {
88
    collection.removeView((View) view);
89
    }
90

  
91
///////////////////////////////////////////////////////////////////////////////////////////////////
92

  
93
  @Override
94
  public int getCount()
95
    {
96
    return mNumTabs;
97
    }
98

  
99
///////////////////////////////////////////////////////////////////////////////////////////////////
100

  
101
  @Override
102
  public boolean isViewFromObject(@NonNull View view, @NonNull Object object)
103
    {
104
    return view == object;
105
    }
106
  }
src/main/java/org/distorted/dialog/RubikDialogPatternView.java
1
///////////////////////////////////////////////////////////////////////////////////////////////////
2
// Copyright 2020 Leszek Koltunski                                                               //
3
//                                                                                               //
4
// This file is part of Magic Cube.                                                              //
5
//                                                                                               //
6
// Magic Cube is free software: you can redistribute it and/or modify                            //
7
// it under the terms of the GNU General Public License as published by                          //
8
// the Free Software Foundation, either version 2 of the License, or                             //
9
// (at your option) any later version.                                                           //
10
//                                                                                               //
11
// Magic Cube is distributed in the hope that it will be useful,                                 //
12
// but WITHOUT ANY WARRANTY; without even the implied warranty of                                //
13
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the                                 //
14
// GNU General Public License for more details.                                                  //
15
//                                                                                               //
16
// You should have received a copy of the GNU General Public License                             //
17
// along with Magic Cube.  If not, see <http://www.gnu.org/licenses/>.                           //
18
///////////////////////////////////////////////////////////////////////////////////////////////////
19

  
20
package org.distorted.dialog;
21

  
22
import android.content.Context;
23
import android.support.v4.app.FragmentActivity;
24
import android.util.AttributeSet;
25
import android.util.DisplayMetrics;
26
import android.view.View;
27
import android.widget.Button;
28
import android.widget.FrameLayout;
29
import android.widget.LinearLayout;
30

  
31
import org.distorted.magic.R;
32
import org.distorted.magic.RubikActivity;
33
import org.distorted.uistate.RubikState;
34

  
35
///////////////////////////////////////////////////////////////////////////////////////////////////
36

  
37
public class RubikDialogPatternView extends FrameLayout
38
  {
39
  private LinearLayout mLayout;
40
  private RubikDialogPattern mDialog;
41

  
42
///////////////////////////////////////////////////////////////////////////////////////////////////
43

  
44
  public RubikDialogPatternView(Context context, AttributeSet attrs, int defStyle)
45
    {
46
    super(context, attrs, defStyle);
47
    }
48

  
49
///////////////////////////////////////////////////////////////////////////////////////////////////
50

  
51
  public RubikDialogPatternView(Context context, AttributeSet attrs)
52
    {
53
    super(context, attrs);
54
    }
55

  
56
///////////////////////////////////////////////////////////////////////////////////////////////////
57

  
58
  public RubikDialogPatternView(FragmentActivity act, RubikDialogPattern dialog, String[] categories)
59
    {
60
    super(act);
61

  
62
    mDialog = dialog;
63
    View tab = inflate( act, R.layout.dialog_pattern_tab, null);
64
    mLayout = tab.findViewById(R.id.tabLayout);
65
    createSection(act,categories);
66

  
67
    addView(tab);
68
    }
69

  
70
///////////////////////////////////////////////////////////////////////////////////////////////////
71

  
72
  private void createSection(final FragmentActivity act, final String[] categories)
73
    {
74
    DisplayMetrics metrics = act.getResources().getDisplayMetrics();
75
    final float scale = metrics.density;
76
    int margin = (int)(3*scale + 0.5f);
77
    LinearLayout.LayoutParams bParams = new LinearLayout.LayoutParams(LinearLayout.LayoutParams.MATCH_PARENT,LinearLayout.LayoutParams.WRAP_CONTENT);
78
    bParams.setMargins(margin, margin, margin, margin);
79

  
80
    final RubikActivity ract = (RubikActivity)getContext();
81

  
82
    for(String category: categories)
83
      {
84
      Button button = new Button(act);
85
      button.setLayoutParams(bParams);
86
      button.setText(category);
87

  
88
      button.setOnClickListener( new View.OnClickListener()
89
        {
90
        @Override
91
        public void onClick(View view)
92
          {
93
          RubikState.switchState(ract,RubikState.PATT);
94
          mDialog.dismiss();
95
          }
96
        });
97

  
98
      mLayout.addView(button);
99
      }
100
    }
101
  }
src/main/java/org/distorted/dialog/RubikDialogScoresView.java
157 157
    {
158 158
    removeAllViews();
159 159

  
160
    View tab = inflate(act, R.layout.dialog_tab, null);
160
    View tab = inflate(act, R.layout.dialog_scores_tab, null);
161 161
    mLayout = tab.findViewById(R.id.tabLayout);
162 162
    addView(tab);
163 163
    }
src/main/java/org/distorted/uistate/RubikStatePattern.java
19 19

  
20 20
package org.distorted.uistate;
21 21

  
22
import android.content.Context;
23 22
import android.content.SharedPreferences;
24
import android.graphics.drawable.BitmapDrawable;
23
import android.os.Bundle;
24
import android.support.v4.app.FragmentManager;
25 25
import android.util.DisplayMetrics;
26
import android.view.Gravity;
27 26
import android.view.LayoutInflater;
28 27
import android.view.View;
29 28
import android.widget.Button;
30
import android.widget.ImageButton;
31 29
import android.widget.LinearLayout;
32
import android.widget.PopupWindow;
33 30
import android.widget.TextView;
34 31

  
32
import org.distorted.dialog.RubikDialogPattern;
35 33
import org.distorted.magic.R;
36 34
import org.distorted.magic.RubikActivity;
37 35
import org.distorted.object.RubikObjectList;
......
41 39

  
42 40
public class RubikStatePattern extends RubikStateAbstract
43 41
  {
44
  private ImageButton mObjButton;
45 42
  private Button mBackButton;
46
  private PopupWindow mPopup;
47
  private int mLayoutWidth, mLayoutHeight;
48
  private LinearLayout mLayout;
49 43
  private int mSize;
50 44

  
51 45
///////////////////////////////////////////////////////////////////////////////////////////////////
......
88 82
      act.changeObject(RubikObjectList.CUBE,mSize);
89 83
      }
90 84

  
85
    FragmentManager mana = act.getSupportFragmentManager();
86
    RubikDialogPattern diag = (RubikDialogPattern) mana.findFragmentByTag(RubikDialogPattern.getDialogTag());
87

  
88
    if( diag==null ) showDialog(mana);
89

  
91 90
    LayoutInflater inflater = act.getLayoutInflater();
92 91

  
93 92
    // TOP ////////////////////////////
......
101 100
    DisplayMetrics metrics = act.getResources().getDisplayMetrics();
102 101
    final float scale = metrics.density;
103 102

  
104
    if( mObjButton==null ) setupObjectButton(act,scale);
105

  
106
    LinearLayout layoutLeft = act.findViewById(R.id.mainBarLeft);
107
    layoutLeft.removeAllViews();
108
    layoutLeft.addView(mObjButton);
109

  
110 103
    if( mBackButton==null ) setupBackButton(act,scale);
111 104

  
112 105
    LinearLayout layoutRight = act.findViewById(R.id.mainBarRight);
113 106
    layoutRight.removeAllViews();
114 107
    layoutRight.addView(mBackButton);
115

  
116
    if( mPopup==null ) setupPopupWindow(act, scale);
117 108
    }
118 109

  
119 110
///////////////////////////////////////////////////////////////////////////////////////////////////
120 111

  
121
  private void setupObjectButton(final RubikActivity act, final float scale)
112
  private void showDialog(FragmentManager manager)
122 113
    {
123
    int padding = (int)(3*scale + 0.5f);
124
    LinearLayout.LayoutParams objectParams = new LinearLayout.LayoutParams(LinearLayout.LayoutParams.WRAP_CONTENT,LinearLayout.LayoutParams.MATCH_PARENT);
125
    mObjButton = new ImageButton(act);
126
    mObjButton.setLayoutParams(objectParams);
127
    mObjButton.setPadding(padding,0,padding,0);
128
    mObjButton.setImageResource(R.drawable.cube_menu);
129

  
130
    mObjButton.setOnClickListener( new View.OnClickListener()
131
      {
132
      @Override
133
      public void onClick(View view)
134
        {
135
        int total = RubikPattern.NUM_CUBES;
136
        boolean vertical = act.isVertical();
137
        mLayout.setOrientation(vertical ? LinearLayout.VERTICAL:LinearLayout.HORIZONTAL);
138

  
139
        int height = view.getHeight();
140
        int width  = view.getWidth();
141
        int laywid = mLayoutWidth * (vertical? 1:total);
142
        int layhei = mLayoutHeight* (vertical? total:1);
143

  
144
        mPopup.showAsDropDown(view, (width-laywid)/2, -height-layhei, Gravity.LEFT);
145
        }
146
      });
114
    Bundle bundle = new Bundle();
115
    int object = RubikObjectList.CUBE.ordinal();
116
    int sizeIndex = RubikObjectList.getSizeIndex(object,mSize);
117
    bundle.putInt("tab", RubikObjectList.pack(object,sizeIndex) );
118

  
119
    RubikDialogPattern diag = new RubikDialogPattern();
120
    diag.setArguments(bundle);
121
    diag.show( manager, RubikDialogPattern.getDialogTag() );
147 122
    }
148 123

  
149 124
///////////////////////////////////////////////////////////////////////////////////////////////////
......
163 138
      @Override
164 139
      public void onClick(View v)
165 140
        {
166
        RubikState.goBack(act);
167
        }
168
      });
169
    }
141
        FragmentManager mana = act.getSupportFragmentManager();
142
        RubikDialogPattern diag = (RubikDialogPattern) mana.findFragmentByTag(RubikDialogPattern.getDialogTag());
170 143

  
171
///////////////////////////////////////////////////////////////////////////////////////////////////
172

  
173
  private void setupPopupWindow(final RubikActivity act, final float scale)
174
    {
175
    LayoutInflater layoutInflater = (LayoutInflater)act.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
176
    final View layout = layoutInflater.inflate(R.layout.popup_objects, null);
177
    mLayout = layout.findViewById(R.id.popup);
178

  
179
    mPopup = new PopupWindow(act);
180
    mPopup.setContentView(layout);
181
    mPopup.setFocusable(true);
182
    int margin = (int)(5*scale + 0.5f);
183

  
184
    BitmapDrawable bd = (BitmapDrawable) act.getResources().getDrawable(R.drawable.cube2);
185
    int cubeWidth  = bd.getIntrinsicWidth();
186
    int cubeHeight = bd.getIntrinsicHeight();
187

  
188
    mLayoutWidth = (int)(cubeWidth + 2*margin + 0.5f);
189
    mLayoutHeight= (int)(cubeHeight+ 2*margin + 0.5f);
190

  
191
    final int[] icons = {R.drawable.cube2, R.drawable.cube3, R.drawable.cube4, R.drawable.cube5 };
192
    final int[] sizes = {2,3,4,5};
193
    int len = icons.length;
194

  
195
    for(int i=0; i<len; i++)
196
      {
197
      final int size = i;
198

  
199
      LinearLayout.LayoutParams p = new LinearLayout.LayoutParams(LinearLayout.LayoutParams.WRAP_CONTENT,LinearLayout.LayoutParams.WRAP_CONTENT);
200
      p.setMargins(margin, margin, margin, margin);
201

  
202
      ImageButton button = new ImageButton(act);
203
      button.setLayoutParams(p);
204

  
205
      button.setBackgroundResource(icons[i]);
206
      button.setOnClickListener( new View.OnClickListener()
207
        {
208
        @Override
209
        public void onClick(View v)
144
        if( diag==null )
210 145
          {
211
          mSize = sizes[size];
212
          act.changeObject(RubikObjectList.CUBE,sizes[size]);
213
          mPopup.dismiss();
146
          showDialog(mana);
214 147
          }
215
        });
216

  
217
      mLayout.addView(button);
218
      }
148
        else
149
          {
150
          diag.dismiss();
151
          RubikState.goBack(act);
152
          }
153
        }
154
      });
219 155
    }
220 156

  
221 157
///////////////////////////////////////////////////////////////////////////////////////////////////
222 158

  
223 159
  public void savePreferences(SharedPreferences.Editor editor)
224 160
    {
225
    mObjButton = null;
226 161
    mBackButton= null;
227

  
228
    if( mPopup!=null )
229
      {
230
      mPopup.dismiss();
231
      mPopup = null;
232
      }
233 162
    }
234 163

  
235 164
///////////////////////////////////////////////////////////////////////////////////////////////////
src/main/res/layout/dialog_pattern_tab.xml
1
<?xml version="1.0" encoding="utf-8"?>
2
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
3
    android:id="@+id/tabScrollView"
4
    android:background="@color/grey"
5
    android:paddingBottom="10dp"
6
    android:layout_width="match_parent"
7
    android:layout_height="match_parent">
8

  
9
    <LinearLayout
10
        android:id="@+id/tabLayout"
11
        android:layout_width="match_parent"
12
        android:layout_height="wrap_content"
13
        android:orientation="vertical" >
14
    </LinearLayout>
15

  
16
</ScrollView>
17

  
src/main/res/layout/dialog_scores_tab.xml
1
<?xml version="1.0" encoding="utf-8"?>
2
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
3
    android:id="@+id/tabScrollView"
4
    android:layout_width="match_parent"
5
    android:layout_height="match_parent">
6

  
7
    <LinearLayout
8
        android:id="@+id/tabLayout"
9
        android:layout_width="match_parent"
10
        android:layout_height="wrap_content"
11
        android:orientation="vertical" >
12
    </LinearLayout>
13

  
14
</ScrollView>
15

  
src/main/res/layout/dialog_tab.xml
1
<?xml version="1.0" encoding="utf-8"?>
2
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
3
    android:id="@+id/tabScrollView"
4
    android:layout_width="match_parent"
5
    android:layout_height="match_parent">
6

  
7
    <LinearLayout
8
        android:id="@+id/tabLayout"
9
        android:layout_width="match_parent"
10
        android:layout_height="wrap_content"
11
        android:orientation="vertical" >
12
    </LinearLayout>
13

  
14
</ScrollView>
15

  

Also available in: Unified diff