0

In My App, user creates a new account by filling some credentials in a dialog box. There is a GridView inside dialog box which different different icons for accounts. User can select any icon for his account while creating the account. The problem is Image is not showing in list view and in DB browser for SQLite too. I don't know what should I do even after too much searching. Here is my try :

Int array containing images : (Many images are in .svg format while others are in .png)

int[] icons = {R.drawable.personalbusaccount, R.drawable.ic_accountant, R.drawable.ic_bank_account,
        R.drawable.multipleaccount, R.drawable.ic_accounting, R.drawable.ic_consultant, R.drawable.choice,
        R.drawable.ic_businesswoman, R.drawable.ic_man, R.drawable.ic_login};

After Button clicked :

 @Override
        public void onClick(View view) {
            AlertDialog.Builder builder = new AlertDialog.Builder(AccountsActivity.this);
            LayoutInflater inflater = getLayoutInflater();
            View v = inflater.inflate(R.layout.new_account_dialog, null);
            final EditText editText = v.findViewById(R.id.et_accname);

            final GridView gv = v.findViewById(R.id.accicon_grid_view);
            NewAccountGAdapter newAccountGAdapter = new NewAccountGAdapter(AccountsActivity.this, icons);
            gv.setAdapter(newAccountGAdapter);

            gv.setOnItemClickListener(new AdapterView.OnItemClickListener() {
                @Override
                public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
                    for (int i = 0; i < gv.getChildCount(); i++) {
                        if(position == i ){
                            gv.getChildAt(i).setBackgroundColor(getResources().getColor(R.color.colorLightGrey));
                            accountIcon = inttoByteArray(icons[position]);
                        }else{
                            gv.getChildAt(i).setBackgroundColor(Color.TRANSPARENT);
                        }
                    }
                }
            });

            builder.setPositiveButton("Create", new DialogInterface.OnClickListener() {
                @Override
                public void onClick(DialogInterface dialog, int which) {
                    accountName = editText.getText().toString();

                    boolean dataAdded = databaseHelper.addAccount(accountIcon, accountName, "0 Rs");
                    if (dataAdded){
                        Toast.makeText(AccountsActivity.this, "Account Created !", Toast.LENGTH_SHORT).show();
                        populateListView();
                    }else {
                        Toast.makeText(AccountsActivity.this, "Account not Created ", Toast.LENGTH_SHORT).show();
                    }

                }
            });

Methods : inttoByteArray() :

private byte[] inttoByteArray(final int i){
        ByteArrayOutputStream bos = new ByteArrayOutputStream();
        DataOutputStream dataOutputStream = new DataOutputStream(bos);
    try {
        dataOutputStream.writeInt(i);
    } catch (IOException e) {
        e.printStackTrace();
    }
    try {
        dataOutputStream.flush();
    } catch (IOException e) {
        e.printStackTrace();
    }
    return bos.toByteArray();
}

In getView() of my custom BaseAdapter :

View view = LayoutInflater.from(context).inflate(R.layout.accounts_list_items, parent, false);
    ImageView imageView = view.findViewById(R.id.acc_icon);
    TextView textViewName = view.findViewById(R.id.tv_accName);
    TextView textViewBlnc = view.findViewById(R.id.tv_accBlnc);

    byte[] icons = accountsModelList.get(position).getIcon();

    Bitmap bm = BitmapFactory.decodeByteArray(icons, 0, icons.length);
    imageView.setImageBitmap(bm);
    textViewName.setText(accountsModelList.get(position).getAccName());
    textViewBlnc.setText(accountsModelList.get(position).getAccBlnc());

DatabaseHelper class :

private static final String TABLE_NAME = "accounts";
private static final String TABLE_COL1 = "acc_id";
private static final String TABLE_COL2 = "acc_icon";
private static final String TABLE_COL3 = "acc_name";
private static final String TABLE_COL4 = "acc_blnc";

 public void onCreate(SQLiteDatabase db) {
    String accountsTable = "CREATE TABLE " + TABLE_NAME + " (" + TABLE_COL1 + " INTEGER PRIMARY KEY AUTOINCREMENT, " +
            TABLE_COL2 + " BLOB, " + TABLE_COL3 + " VARCHAR(300), " + TABLE_COL4 + " VARCHAR(500))";

db.execSQL(accountsTable);
}

public boolean addAccount(byte[] icon, String acName, String acBlnc){
    SQLiteDatabase db = this.getWritableDatabase();
        ContentValues contentValues = new ContentValues();
        contentValues.put(TABLE_COL2, icon);
        contentValues.put(TABLE_COL3, acName);
        contentValues.put(TABLE_COL4, acBlnc);
        return db.insert(TABLE_NAME, null, contentValues)>0;
}

Please I need some help !

Usama Sajid
  • 61
  • 2
  • 10
  • The `icons` array is simple `int`s, so `icons[position]` is a single `int`. If that's actually what you're trying to store, there's no need for the `ByteArrayOutputStream`, `DataOutputStream`, etc. Just save the `int`. Beyond that, I don't see any code related to a database in your post. – Mike M. Aug 24 '19 at 12:42
  • I have added my database code above. I just want to store image in database and the retrieve it too. It doesnt matter if it is in int or byte array. So please help me out here ! – Usama Sajid Aug 24 '19 at 16:13
  • You don't want to store images in a database. It's just bad. If the images are only ever going to be in your resources – i.e., they will always have an `R.drawable` – it'd be better to store that somehow, and load them from resources when needed. Since the `int` ID can change when you rebuild, probably the easiest reliable thing to do would be to store the resource name in the DB, and change it back to the `int` when retrieving it. Have a look at the 2nd code block in [this answer](https://stackoverflow.com/a/56088157), which you can use to change between the resource name and the `int` value. – Mike M. Aug 24 '19 at 17:05
  • then how can i get the resource name of selected icon ? – Usama Sajid Aug 24 '19 at 17:45
  • With the `iconName()` method there. For example, if you call `String name = iconName(icons[0]);`, then `name` will be `"personalbusaccount"`, and that's what would be stored in the database. When you need to load the image, you will get a value of `"personalbusaccount"` from your `Cursor` – e.g., `String iconName = cursor.getString(...);` – and you would pass that to the `iconRes()` method there – `int resId = iconRes(iconName);`. Then you can use that with `ImageView#setImageResource(resId)`, `getDrawable(resId)`, etc. – Mike M. Aug 24 '19 at 18:01
  • What will be the iconName() method ? – Usama Sajid Aug 24 '19 at 18:27
  • The `iconName()` and `iconRes()` methods are those in the second code block in [the answer I linked you to earlier](https://stackoverflow.com/a/56088157). – Mike M. Aug 24 '19 at 18:31
  • I am trying this but its returning null. 'Bitmap largeIcon = BitmapFactory.decodeResource(getResources(),iconRes(getResources().getResourceName(icons[position]))); ' and app is crashed – Usama Sajid Aug 25 '19 at 06:12
  • What kind of files are your drawables? That is, are they `jpg`s, or `png`s, or `xml`s, etc.? – Mike M. Aug 25 '19 at 06:19
  • most of them are svgs and others are pngs – Usama Sajid Aug 25 '19 at 06:25
  • I have tried this too but image is not shown in db browser.. int ic = iconRes(iconName(icons[position])); accountIcon = inttoByteArray(ic); – Usama Sajid Aug 25 '19 at 06:25
  • `BitmapFactory` will not work with `svg`s. It only handles raster images, like `bmp`, `jpg`, `png`, etc. When you're loading the images, you don't really need `Bitmap`s. You just need a `Drawable`s. Use `getDrawable()` or `ContextCompat.getDrawable()` instead to get those. – Mike M. Aug 25 '19 at 06:30
  • And get rid of that `inttoByteArray()` method. You don't need it anymore. You're simply saving a `String` in the database, now. – Mike M. Aug 25 '19 at 06:31
  • Can you please give the coded answer ? Sorry I am new to android and I dont know much. and How can i retrieve it too – Usama Sajid Aug 25 '19 at 06:34
  • Here: https://drive.google.com/file/d/10vDLiGU0hD1pYmmqiLRLUIzIDojsINJa/view?usp=drivesdk. I just stuck those icon methods in the `AccountsActivity`, and made them `static`. You might want to put them in a utility class instead. – Mike M. Aug 25 '19 at 07:44
  • Thanks Sir ! Its done. Much respect for you you were very humble – Usama Sajid Aug 25 '19 at 10:15

0 Answers0