List of usage examples for android.text Spannable getSpanStart
public int getSpanStart(Object tag);
From source file:com.slx.funstream.adapters.ChatAdapter.java
private void linksToImages(Spannable spannable, TextView textView) { // Matcher matcher = Linkify.WEB_URLS.matcher(spannable); // URLSpan[] spans = textView.getUrls(); URLSpan[] spans = spannable.getSpans(0, spannable.length(), URLSpan.class); Log.d(TAG, "URLSpan[] size=" + spans.length); for (URLSpan span : spans) { String url = span.getURL(); Log.d(TAG, "START: " + spannable.getSpanStart(span) + "END: " + spannable.getSpanEnd(span) + " " + url); ImageTarget t = new ImageTarget(spannable.getSpanStart(span), spannable.getSpanEnd(span), textView, spannable);//from w w w . j av a 2 s . c o m picasso.load(url).resize(300, 300).centerInside().onlyScaleDown().into(t); targets.add(t); } }
From source file:org.telegram.ui.GroupCreateActivity.java
@Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { if (fragmentView == null) { fragmentView = inflater.inflate(R.layout.group_create_layout, container, false); epmtyTextView = (TextView) fragmentView.findViewById(R.id.searchEmptyView); userSelectEditText = (EditText) fragmentView.findViewById(R.id.bubble_input_text); countTextView = (TextView) fragmentView.findViewById(R.id.bubble_counter_text); if (Build.VERSION.SDK_INT >= 11) { userSelectEditText.setTextIsSelectable(false); }// www . j av a 2 s. c om userSelectEditText.addTextChangedListener(new TextWatcher() { @Override public void beforeTextChanged(CharSequence charSequence, int start, int count, int after) { if (!ignoreChange) { beforeChangeIndex = userSelectEditText.getSelectionStart(); changeString = new SpannableString(charSequence); } } @Override public void onTextChanged(CharSequence charSequence, int i, int i2, int i3) { } @Override public void afterTextChanged(Editable editable) { if (!ignoreChange) { boolean search = false; int afterChangeIndex = userSelectEditText.getSelectionEnd(); if (editable.toString().length() < changeString.toString().length()) { String deletedString = ""; try { deletedString = changeString.toString().substring(afterChangeIndex, beforeChangeIndex); } catch (Exception e) { FileLog.e("tmessages", e); } if (deletedString.length() > 0) { if (searching && searchWas) { search = true; } Spannable span = userSelectEditText.getText(); for (int a = 0; a < allSpans.size(); a++) { Emoji.XImageSpan sp = allSpans.get(a); if (span.getSpanStart(sp) == -1) { allSpans.remove(sp); selectedContacts.remove(sp.uid); } } if (selectedContacts.isEmpty()) { doneTextView.setText(getStringEntry(R.string.Done)); } else { doneTextView.setText( getStringEntry(R.string.Done) + " (" + selectedContacts.size() + ")"); } countTextView.setText(selectedContacts.size() + "/200"); listView.invalidateViews(); } else { search = true; } } else { search = true; } if (search) { String text = userSelectEditText.getText().toString().replace("<", ""); if (text.length() != 0) { searchDialogs(text); searching = true; searchWas = true; epmtyTextView.setText(getStringEntry(R.string.NoResult)); listViewAdapter.notifyDataSetChanged(); } else { searchResult = null; searchResultNames = null; searching = false; searchWas = false; epmtyTextView.setText(getStringEntry(R.string.NoContacts)); listViewAdapter.notifyDataSetChanged(); } } } } }); listView = (PinnedHeaderListView) fragmentView.findViewById(R.id.listView); listView.setEmptyView(epmtyTextView); listView.setVerticalScrollBarEnabled(false); listView.setAdapter(listViewAdapter = new ListAdapter(parentActivity)); listView.setOnItemClickListener(new AdapterView.OnItemClickListener() { @Override public void onItemClick(AdapterView<?> adapterView, View view, int i, long l) { TLRPC.User user; int section = listViewAdapter.getSectionForPosition(i); int row = listViewAdapter.getPositionInSectionForPosition(i); if (searching && searchWas) { user = searchResult.get(row); } else { ArrayList<TLRPC.TL_contact> arr = ContactsController.Instance.usersSectionsDict .get(ContactsController.Instance.sortedUsersSectionsArray.get(section)); user = MessagesController.Instance.users.get(arr.get(row).user_id); listView.invalidateViews(); } if (selectedContacts.containsKey(user.id)) { Emoji.XImageSpan span = selectedContacts.get(user.id); selectedContacts.remove(user.id); SpannableStringBuilder text = new SpannableStringBuilder(userSelectEditText.getText()); text.delete(text.getSpanStart(span), text.getSpanEnd(span)); allSpans.remove(span); ignoreChange = true; userSelectEditText.setText(text); userSelectEditText.setSelection(text.length()); ignoreChange = false; } else { if (selectedContacts.size() == 200) { return; } ignoreChange = true; Emoji.XImageSpan span = createAndPutChipForUser(user); span.uid = user.id; ignoreChange = false; } if (selectedContacts.isEmpty()) { doneTextView.setText(getStringEntry(R.string.Done)); } else { doneTextView.setText(getStringEntry(R.string.Done) + " (" + selectedContacts.size() + ")"); } countTextView.setText(selectedContacts.size() + "/200"); if (searching || searchWas) { searching = false; searchWas = false; epmtyTextView.setText(getStringEntry(R.string.NoContacts)); ignoreChange = true; SpannableStringBuilder ssb = new SpannableStringBuilder(""); for (ImageSpan sp : allSpans) { ssb.append("<<"); ssb.setSpan(sp, ssb.length() - 2, ssb.length(), SpannableStringBuilder.SPAN_EXCLUSIVE_EXCLUSIVE); } userSelectEditText.setText(ssb); userSelectEditText.setSelection(ssb.length()); ignoreChange = false; listViewAdapter.notifyDataSetChanged(); } else { listView.invalidateViews(); } } }); } else { ViewGroup parent = (ViewGroup) fragmentView.getParent(); if (parent != null) { parent.removeView(fragmentView); } } return fragmentView; }
From source file:im.zico.fancy.common.widget.HackyMovementMethod.java
@Override public boolean onTouchEvent(TextView widget, Spannable buffer, MotionEvent event) { if (mGray == null) { mGray = new BackgroundColorSpan( ContextCompat.getColor(widget.getContext(), R.color.alpha_spannable_pressed)); }//from w ww .j a va2s . c o m mIsLinkHit = false; int action = event.getAction(); if (action == MotionEvent.ACTION_DOWN || action == MotionEvent.ACTION_UP) { int x = (int) event.getX(); int y = (int) event.getY(); x -= widget.getTotalPaddingLeft(); y -= widget.getTotalPaddingTop(); x += widget.getScrollX(); y += widget.getScrollY(); int line = widget.getLayout().getLineForVertical(y); int offset = widget.getLayout().getOffsetForHorizontal(line, x); ClickableSpan[] spans = buffer.getSpans(offset, offset, ClickableSpan.class); if (spans.length != 0) { int start = buffer.getSpanStart(spans[0]); int end = buffer.getSpanEnd(spans[0]); mIsLinkHit = true; if (action == MotionEvent.ACTION_DOWN) { buffer.setSpan(mGray, start, end, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE); } else if (action == MotionEvent.ACTION_UP) { spans[0].onClick(widget); buffer.removeSpan(mGray); } return true; } } else { buffer.removeSpan(mGray); } return Touch.onTouchEvent(widget, buffer, event); }
From source file:com.yahala.ui.GroupCreateActivity.java
@Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { if (fragmentView == null) { searching = false;//from w ww . j a va2 s.c o m searchWas = false; fragmentView = inflater.inflate(R.layout.group_create_layout, container, false); emptyTextView = (TextView) fragmentView.findViewById(R.id.searchEmptyView); emptyTextView.setText(LocaleController.getString("NoContacts", R.string.NoContacts)); userSelectEditText = (EditText) fragmentView.findViewById(R.id.bubble_input_text); userSelectEditText.setHint(LocaleController.getString("SendMessageTo", R.string.SendMessageTo)); if (Build.VERSION.SDK_INT >= 11) { userSelectEditText.setTextIsSelectable(false); } userSelectEditText.addTextChangedListener(new TextWatcher() { @Override public void beforeTextChanged(CharSequence charSequence, int start, int count, int after) { if (!ignoreChange) { beforeChangeIndex = userSelectEditText.getSelectionStart(); changeString = new SpannableString(charSequence); } } @Override public void onTextChanged(CharSequence charSequence, int i, int i2, int i3) { } @Override public void afterTextChanged(Editable editable) { if (!ignoreChange) { boolean search = false; int afterChangeIndex = userSelectEditText.getSelectionEnd(); if (editable.toString().length() < changeString.toString().length()) { String deletedString = ""; try { deletedString = changeString.toString().substring(afterChangeIndex, beforeChangeIndex); } catch (Exception e) { FileLog.e("tmessages", e); } if (deletedString.length() > 0) { if (searching && searchWas) { search = true; } Spannable span = userSelectEditText.getText(); for (int a = 0; a < allSpans.size(); a++) { XImageSpan sp = allSpans.get(a); if (span.getSpanStart(sp) == -1) { allSpans.remove(sp); selectedContacts.remove(sp.jid); } } if (parentActivity != null) { ActionBar actionBar = parentActivity.getSupportActionBar(); actionBar.setSubtitle(String.format("%d/200 %s", selectedContacts.size(), LocaleController.getString("Members", R.string.Members))); } listView.invalidateViews(); } else { search = true; } } else { search = true; } if (search) { String text = userSelectEditText.getText().toString().replace("<", ""); if (text.length() != 0) { searchDialogs(text); searching = true; searchWas = true; emptyTextView.setText(LocaleController.getString("NoResult", R.string.NoResult)); listViewAdapter.notifyDataSetChanged(); } else { searchResult = null; searchResultNames = null; searching = false; searchWas = false; emptyTextView .setText(LocaleController.getString("NoContacts", R.string.NoContacts)); listViewAdapter.notifyDataSetChanged(); } } } } }); listView = (PinnedHeaderListView) fragmentView.findViewById(R.id.listView); listView.setEmptyView(emptyTextView); listView.setVerticalScrollBarEnabled(false); listView.setAdapter(listViewAdapter = new ListAdapter(parentActivity)); listView.setOnItemClickListener(new AdapterView.OnItemClickListener() { @Override public void onItemClick(AdapterView<?> adapterView, View view, int i, long l) { TLRPC.User user; int section = listViewAdapter.getSectionForPosition(i); int row = listViewAdapter.getPositionInSectionForPosition(i); if (searching && searchWas) { user = searchResult.get(row); } else { ArrayList<TLRPC.User> arr = com.yahala.xmpp.ContactsController .getInstance().usersSectionsDict.get( com.yahala.xmpp.ContactsController.getInstance().sortedUsersSectionsArray .get(section)); user = com.yahala.xmpp.ContactsController.getInstance().friendsDict.get(arr.get(row).jid); listView.invalidateViews(); } if (selectedContacts.containsKey(user.jid)) { XImageSpan span = selectedContacts.get(user.jid); selectedContacts.remove(user.jid); SpannableStringBuilder text = new SpannableStringBuilder(userSelectEditText.getText()); text.delete(text.getSpanStart(span), text.getSpanEnd(span)); allSpans.remove(span); ignoreChange = true; userSelectEditText.setText(text); userSelectEditText.setSelection(text.length()); ignoreChange = false; } else { if (selectedContacts.size() == 200) { return; } ignoreChange = true; XImageSpan span = createAndPutChipForUser(user); span.jid = user.jid; ignoreChange = false; } if (parentActivity != null) { ActionBar actionBar = parentActivity.getSupportActionBar(); actionBar.setSubtitle(String.format("%d/200 %s", selectedContacts.size(), LocaleController.getString("Members", R.string.Members))); } if (searching || searchWas) { searching = false; searchWas = false; emptyTextView.setText(LocaleController.getString("NoContacts", R.string.NoContacts)); ignoreChange = true; SpannableStringBuilder ssb = new SpannableStringBuilder(""); for (ImageSpan sp : allSpans) { ssb.append("<<"); ssb.setSpan(sp, ssb.length() - 2, ssb.length(), SpannableStringBuilder.SPAN_EXCLUSIVE_EXCLUSIVE); } userSelectEditText.setText(ssb); userSelectEditText.setSelection(ssb.length()); ignoreChange = false; listViewAdapter.notifyDataSetChanged(); } else { listView.invalidateViews(); } } }); } else { ViewGroup parent = (ViewGroup) fragmentView.getParent(); if (parent != null) { parent.removeView(fragmentView); } } return fragmentView; }
From source file:android.melbournehistorymap.MapsActivity.java
/** * Manipulates the map once available./*from ww w . j a v a2 s . c om*/ * This callback is triggered when the map is ready to be used. * This is where we can add markers or lines, add listeners or move the camera. In this case, * we just add a marker near Sydney, Australia. * If Google Play services is not installed on the device, the user will be prompted to install * it inside the SupportMapFragment. This method will only be triggered once the user has * installed Google Play services and returned to the app. */ @Override public void onMapReady(GoogleMap googleMap) { mMap = googleMap; spinner = (ProgressBar) findViewById(R.id.prograssSpinner); //check if permission has been granted if (ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) { // Permission has already been granted return; } mMap.setMyLocationEnabled(true); mMap.getUiSettings().setZoomControlsEnabled(false); double lat; double lng; final int radius; int zoom; lat = Double.parseDouble(CurrLat); lng = Double.parseDouble(CurrLong); //build current location LatLng currentLocation = new LatLng(lat, lng); final LatLng realLocation = currentLocation; if (MELBOURNE.contains(currentLocation)) { mMap.getUiSettings().setMyLocationButtonEnabled(true); zoom = 17; } else { mMap.getUiSettings().setMyLocationButtonEnabled(false); lat = -37.81161508043379; lng = 144.9647320434451; zoom = 15; currentLocation = new LatLng(lat, lng); } mMap.animateCamera(CameraUpdateFactory.newLatLngZoom(currentLocation, 13)); CameraPosition cameraPosition = new CameraPosition.Builder().target(currentLocation) // Sets the center of the map to location user .zoom(zoom) // Sets the zoom .bearing(0) // Sets the orientation of the camera to east .tilt(25) // Sets the tilt of the camera to 30 degrees .build(); // Creates a CameraPosition from the builder //Animate user to map location, if in Melbourne or outside of Melbourne bounds mMap.animateCamera(CameraUpdateFactory.newCameraPosition(cameraPosition), new GoogleMap.CancelableCallback() { @Override public void onFinish() { updateMap(); } @Override public void onCancel() { } }); final TextView placeTitle = (TextView) findViewById(R.id.placeTitle); final TextView placeVic = (TextView) findViewById(R.id.placeVic); final TextView expPlaceTitle = (TextView) findViewById(R.id.expPlaceTitle); final TextView expPlaceVic = (TextView) findViewById(R.id.expPlaceVic); final TextView expPlaceDescription = (TextView) findViewById(R.id.placeDescription); final TextView wikiLicense = (TextView) findViewById(R.id.wikiLicense); final TextView expPlaceDistance = (TextView) findViewById(R.id.expPlaceDistance); final RelativeLayout tile = (RelativeLayout) findViewById(R.id.tile); final TextView fab = (TextView) findViewById(R.id.fab); final RelativeLayout distanceCont = (RelativeLayout) findViewById(R.id.distanceContainer); // String license = "Text is available under the <a rel=\"license\" href=\"//en.wikipedia.org/wiki/Wikipedia:Text_of_Creative_Commons_Attribution-ShareAlike_3.0_Unported_License\">Creative Commons Attribution-ShareAlike License</a><a rel=\"license\" href=\"//creativecommons.org/licenses/by-sa/3.0/\" style=\"display:none;\"></a>;\n" + // "additional terms may apply."; // wikiLicense.setText(Html.fromHtml(license)); // wikiLicense.setMovementMethod(LinkMovementMethod.getInstance()); //Marker click mMap.setOnMarkerClickListener(new GoogleMap.OnMarkerClickListener() { @Override public boolean onMarkerClick(Marker marker) { String title = marker.getTitle(); mMap.setPadding(0, 0, 0, 620); //set clicked marker to full opacity marker.setAlpha(1f); //set previous marker back to partial opac (if there is a prevMarker if (dirtyMarker == 1) { prevMarker.setAlpha(0.6f); } prevMarker = marker; dirtyMarker = 1; //Set DB helper DBHelper myDBHelper = new DBHelper(MapsActivity.this, WikiAPI.DB_NAME, null, WikiAPI.VERSION); //Only search for Wiki API requests if no place article returned. // ** //Open DB as readable only. SQLiteDatabase db = myDBHelper.getReadableDatabase(); //Set the query String dbFriendlyName = title.replace("\'", "\'\'"); //Limit by 1 rows Cursor cursor = db.query(DBHelper.TABLE_NAME, null, "PLACE_NAME = '" + dbFriendlyName + "'", null, null, null, null, "1"); //move through each row returned in the query results while (cursor.moveToNext()) { String place_ID = cursor.getString(cursor.getColumnIndex("PLACE_ID")); String placeName = cursor.getString(cursor.getColumnIndex("PLACE_NAME")); String placeLoc = cursor.getString(cursor.getColumnIndex("PLACE_LOCATION")); String placeArticle = cursor.getString(cursor.getColumnIndex("ARTICLE")); String placeLat = cursor.getString(cursor.getColumnIndex("LAT")); String placeLng = cursor.getString(cursor.getColumnIndex("LNG")); //Get Google Place photos //Source: https://developers.google.com/places/android-api/photos final String placeId = place_ID; Places.GeoDataApi.getPlacePhotos(mGoogleApiClient, placeId) .setResultCallback(new ResultCallback<PlacePhotoMetadataResult>() { @Override public void onResult(PlacePhotoMetadataResult photos) { if (!photos.getStatus().isSuccess()) { return; } ImageView mImageView = (ImageView) findViewById(R.id.imageView); ImageView mImageViewExpanded = (ImageView) findViewById(R.id.headerImage); TextView txtAttribute = (TextView) findViewById(R.id.photoAttribute); TextView expTxtAttribute = (TextView) findViewById(R.id.expPhotoAttribute); PlacePhotoMetadataBuffer photoMetadataBuffer = photos.getPhotoMetadata(); if (photoMetadataBuffer.getCount() > 0) { // Display the first bitmap in an ImageView in the size of the view photoMetadataBuffer.get(0).getScaledPhoto(mGoogleApiClient, 600, 200) .setResultCallback(mDisplayPhotoResultCallback); //get photo attributions PlacePhotoMetadata photo = photoMetadataBuffer.get(0); CharSequence attribution = photo.getAttributions(); if (attribution != null) { txtAttribute.setText(Html.fromHtml(String.valueOf(attribution))); expTxtAttribute.setText(Html.fromHtml(String.valueOf(attribution))); //http://stackoverflow.com/questions/4303160/how-can-i-make-links-in-fromhtml-clickable-android txtAttribute.setMovementMethod(LinkMovementMethod.getInstance()); expTxtAttribute.setMovementMethod(LinkMovementMethod.getInstance()); } else { txtAttribute.setText(" "); expTxtAttribute.setText(" "); } } else { //Reset image view as no photo was identified mImageView.setImageResource(android.R.color.transparent); mImageViewExpanded.setImageResource(android.R.color.transparent); txtAttribute.setText(R.string.no_photos); expTxtAttribute.setText(R.string.no_photos); } photoMetadataBuffer.release(); } }); LatLng destLocation = new LatLng(Double.parseDouble(placeLat), Double.parseDouble(placeLng)); //Work out distance between current location and place location //Source Library: https://github.com/googlemaps/android-maps-utils double distance = SphericalUtil.computeDistanceBetween(realLocation, destLocation); distance = Math.round(distance); distance = distance * 0.001; String strDistance = String.valueOf(distance); String[] arrDistance = strDistance.split("\\."); String unit = "km"; if (arrDistance[0] == "0") { unit = "m"; strDistance = arrDistance[1]; } else { strDistance = arrDistance[0] + "." + arrDistance[1].substring(0, 1); } placeArticle = placeArticle .replaceAll("(<div class=\"thumb t).*\\s.*\\s.*\\s.*\\s.*\\s<\\/div>\\s<\\/div>", " "); Spannable noUnderlineMessage = new SpannableString(Html.fromHtml(placeArticle)); //http://stackoverflow.com/questions/4096851/remove-underline-from-links-in-textview-android for (URLSpan u : noUnderlineMessage.getSpans(0, noUnderlineMessage.length(), URLSpan.class)) { noUnderlineMessage.setSpan(new UnderlineSpan() { public void updateDrawState(TextPaint tp) { tp.setUnderlineText(false); } }, noUnderlineMessage.getSpanStart(u), noUnderlineMessage.getSpanEnd(u), 0); } placeArticle = String.valueOf(noUnderlineMessage); placeArticle = placeArticle.replaceAll("(\\[\\d\\])", " "); placeTitle.setText(placeName); expPlaceTitle.setText(placeName); placeVic.setText(placeLoc); expPlaceVic.setText(placeLoc); expPlaceDescription.setText(placeArticle); if (MELBOURNE.contains(realLocation)) { expPlaceDistance.setText("Distance: " + strDistance + unit); distanceCont.setVisibility(View.VISIBLE); } } tile.setVisibility(View.VISIBLE); fab.setVisibility(View.VISIBLE); //Set to true to not show default behaviour. return false; } }); mMap.setOnMapClickListener(new GoogleMap.OnMapClickListener() { @Override public void onMapClick(LatLng latLng) { int viewStatus = tile.getVisibility(); if (viewStatus == View.VISIBLE) { tile.setVisibility(View.INVISIBLE); fab.setVisibility(View.INVISIBLE); //set previous marker back to partial opac (if there is a prevMarker if (dirtyMarker == 1) { prevMarker.setAlpha(0.6f); } } mMap.setPadding(0, 0, 0, 0); } }); FloatingActionButton shareIcon = (FloatingActionButton) findViewById(R.id.shareIcon); shareIcon.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { //https://www.google.com.au/maps/place/Federation+Square/@-37.8179789,144.9668635,15z //Build implicit intent by triggering a SENDTO action, which will capture applications that allow for messages //that allow for messages to be sent to a specific user with data //http://developer.android.com/reference/android/content/Intent.html#ACTION_SENDTO Intent intent = new Intent(Intent.ACTION_SEND); intent.setType("text/plain"); //Build SMS String encodedPlace = "empty"; try { encodedPlace = URLEncoder.encode(String.valueOf(expPlaceTitle.getText()), "UTF-8"); } catch (UnsupportedEncodingException e) { e.printStackTrace(); } intent.putExtra(Intent.EXTRA_TEXT, String.valueOf(expPlaceTitle.getText()) + " \n\nhttps://www.google.com.au/maps/place/" + encodedPlace); Intent sms = Intent.createChooser(intent, null); startActivity(sms); } }); TextView fullArticle = (TextView) findViewById(R.id.fullArticle); fullArticle.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { String wikiPlace = WikiPlace.getName(String.valueOf(expPlaceTitle.getText())); String url = "https://en.wikipedia.org/wiki/" + wikiPlace; Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(url)); startActivity(browserIntent); } }); }
From source file:android.support.text.emoji.EmojiProcessor.java
/** * Checks a given CharSequence for emojis, and adds EmojiSpans if any emojis are found. * <p>/*from w w w . ja v a2 s . c o m*/ * <ul> * <li>If no emojis are found, {@code charSequence} given as the input is returned without * any changes. i.e. charSequence is a String, and no emojis are found, the same String is * returned.</li> * <li>If the given input is not a Spannable (such as String), and at least one emoji is found * a new {@link android.text.Spannable} instance is returned. </li> * <li>If the given input is a Spannable, the same instance is returned. </li> * </ul> * * @param charSequence CharSequence to add the EmojiSpans, cannot be {@code null} * @param start start index in the charSequence to look for emojis, should be greater than or * equal to {@code 0}, also less than {@code charSequence.length()} * @param end end index in the charSequence to look for emojis, should be greater than or * equal to {@code start} parameter, also less than {@code charSequence.length()} * @param maxEmojiCount maximum number of emojis in the {@code charSequence}, should be greater * than or equal to {@code 0} * @param replaceAll whether to replace all emoji with {@link EmojiSpan}s */ CharSequence process(@NonNull final CharSequence charSequence, @IntRange(from = 0) int start, @IntRange(from = 0) int end, @IntRange(from = 0) int maxEmojiCount, final boolean replaceAll) { final boolean isSpannableBuilder = charSequence instanceof SpannableBuilder; if (isSpannableBuilder) { ((SpannableBuilder) charSequence).beginBatchEdit(); } try { Spannable spannable = null; // if it is a spannable already, use the same instance to add/remove EmojiSpans. // otherwise wait until the the first EmojiSpan found in order to change the result // into a Spannable. if (isSpannableBuilder || charSequence instanceof Spannable) { spannable = (Spannable) charSequence; } if (spannable != null) { final EmojiSpan[] spans = spannable.getSpans(start, end, EmojiSpan.class); if (spans != null && spans.length > 0) { // remove existing spans, and realign the start, end according to spans // if start or end is in the middle of an emoji they should be aligned final int length = spans.length; for (int index = 0; index < length; index++) { final EmojiSpan span = spans[index]; final int spanStart = spannable.getSpanStart(span); final int spanEnd = spannable.getSpanEnd(span); // Remove span only when its spanStart is NOT equal to current end. // During add operation an emoji at index 0 is added with 0-1 as start and // end indices. Therefore if there are emoji spans at [0-1] and [1-2] // and end is 1, the span between 0-1 should be deleted, not 1-2. if (spanStart != end) { spannable.removeSpan(span); } start = Math.min(spanStart, start); end = Math.max(spanEnd, end); } } } if (start == end || start >= charSequence.length()) { return charSequence; } // calculate max number of emojis that can be added. since getSpans call is a relatively // expensive operation, do it only when maxEmojiCount is not unlimited. if (maxEmojiCount != EmojiCompat.EMOJI_COUNT_UNLIMITED && spannable != null) { maxEmojiCount -= spannable.getSpans(0, spannable.length(), EmojiSpan.class).length; } // add new ones int addedCount = 0; final ProcessorSm sm = new ProcessorSm(mMetadataRepo.getRootNode()); int currentOffset = start; int codePoint = Character.codePointAt(charSequence, currentOffset); while (currentOffset < end && addedCount < maxEmojiCount) { final int action = sm.check(codePoint); switch (action) { case ACTION_ADVANCE_BOTH: start += Character.charCount(Character.codePointAt(charSequence, start)); currentOffset = start; if (currentOffset < end) { codePoint = Character.codePointAt(charSequence, currentOffset); } break; case ACTION_ADVANCE_END: currentOffset += Character.charCount(codePoint); if (currentOffset < end) { codePoint = Character.codePointAt(charSequence, currentOffset); } break; case ACTION_FLUSH: if (replaceAll || !hasGlyph(charSequence, start, currentOffset, sm.getFlushMetadata())) { if (spannable == null) { spannable = new SpannableString(charSequence); } addEmoji(spannable, sm.getFlushMetadata(), start, currentOffset); addedCount++; } start = currentOffset; break; } } // After the last codepoint is consumed the state machine might be in a state where it // identified an emoji before. i.e. abc[women-emoji] when the last codepoint is consumed // state machine is waiting to see if there is an emoji sequence (i.e. ZWJ). // Need to check if it is in such a state. if (sm.isInFlushableState() && addedCount < maxEmojiCount) { if (replaceAll || !hasGlyph(charSequence, start, currentOffset, sm.getCurrentMetadata())) { if (spannable == null) { spannable = new SpannableString(charSequence); } addEmoji(spannable, sm.getCurrentMetadata(), start, currentOffset); addedCount++; } } return spannable == null ? charSequence : spannable; } finally { if (isSpannableBuilder) { ((SpannableBuilder) charSequence).endBatchEdit(); } } }
From source file:cgeo.geocaching.CacheDetailActivity.java
private static void fixTextColor(final Spannable spannable, final int backgroundColor) { final ForegroundColorSpan[] spans = spannable.getSpans(0, spannable.length(), ForegroundColorSpan.class); for (final ForegroundColorSpan span : spans) { if (ColorUtils.getContrastRatio(span.getForegroundColor(), backgroundColor) < CONTRAST_THRESHOLD) { final int start = spannable.getSpanStart(span); final int end = spannable.getSpanEnd(span); // Assuming that backgroundColor can be either white or black, // this will set opposite background color (white for black and black for white) spannable.setSpan(new BackgroundColorSpan(backgroundColor ^ 0x00ffffff), start, end, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE); }/*from ww w .j a v a 2s . co m*/ } }
From source file:com.hippo.nimingban.ui.ListActivity.java
private Spanned fixURLSpan(Spanned spanned) { Spannable spannable; if (spanned instanceof Spannable) { spannable = (Spannable) spanned; } else {// www .j a va 2s .co m spannable = new SpannableString(spanned); } URLSpan[] urlSpans = spannable.getSpans(0, spanned.length(), URLSpan.class); if (urlSpans == null) { return spanned; } for (URLSpan urlSpan : urlSpans) { String url = urlSpan.getURL(); if (TextUtils.isEmpty(url)) { spannable.removeSpan(urlSpan); } try { new URL(url); } catch (MalformedURLException e) { URL absoluteUrl; // It might be relative path try { // Use absolute url absoluteUrl = new URL(new URL(ACUrl.HOST), url); int start = spannable.getSpanStart(urlSpan); int end = spannable.getSpanEnd(urlSpan); spannable.removeSpan(urlSpan); spannable.setSpan(new URLSpan(absoluteUrl.toString()), start, end, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE); } catch (MalformedURLException e1) { // Can't get url spannable.removeSpan(urlSpan); } } } return spannable; }
From source file:com.tct.mail.browse.MessageHeaderView.java
private void stripUnderlines(TextView textView, Account account) { final Spannable spannable = (Spannable) textView.getText(); final URLSpan[] urls = textView.getUrls(); for (URLSpan span : urls) { final int start = spannable.getSpanStart(span); final int end = spannable.getSpanEnd(span); spannable.removeSpan(span);/*from w w w . ja v a 2 s .c o m*/ //TS: rong-tang 2016-04-19 EMAIL BUGFIX-1951808 MOD_S span = new EmailAddressSpan(getContext(), account, span.getURL().substring(7), mContactInfoSource); ((EmailAddressSpan) span).setFragmentManager(mFragmentManager); //TS: rong-tang 2016-04-19 EMAIL BUGFIX-1951808 MOD_E spannable.setSpan(span, start, end, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE); } }
From source file:org.telegram.ui.ChannelCreateActivity.java
@Override public View createView(Context context) { searching = false;/* w w w . jav a 2s.c o m*/ searchWas = false; actionBar.setBackButtonImage(R.drawable.ic_ab_back); actionBar.setAllowOverlayTitle(true); actionBar.setActionBarMenuOnItemClick(new ActionBar.ActionBarMenuOnItemClick() { @Override public void onItemClick(int id) { if (id == -1) { finishFragment(); } else if (id == done_button) { if (currentStep == 0) { if (donePressed) { return; } if (nameTextView.length() == 0) { Vibrator v = (Vibrator) getParentActivity().getSystemService(Context.VIBRATOR_SERVICE); if (v != null) { v.vibrate(200); } AndroidUtilities.shakeView(nameTextView, 2, 0); return; } donePressed = true; if (avatarUpdater.uploadingAvatar != null) { createAfterUpload = true; progressDialog = new ProgressDialog(getParentActivity()); progressDialog.setMessage(LocaleController.getString("Loading", R.string.Loading)); progressDialog.setCanceledOnTouchOutside(false); progressDialog.setCancelable(false); progressDialog.setButton(DialogInterface.BUTTON_NEGATIVE, LocaleController.getString("Cancel", R.string.Cancel), new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { createAfterUpload = false; progressDialog = null; donePressed = false; try { dialog.dismiss(); } catch (Exception e) { FileLog.e("tmessages", e); } } }); progressDialog.show(); return; } final int reqId = MessagesController.getInstance().createChat( nameTextView.getText().toString(), new ArrayList<Integer>(), descriptionTextView.getText().toString(), ChatObject.CHAT_TYPE_CHANNEL, ChannelCreateActivity.this); progressDialog = new ProgressDialog(getParentActivity()); progressDialog.setMessage(LocaleController.getString("Loading", R.string.Loading)); progressDialog.setCanceledOnTouchOutside(false); progressDialog.setCancelable(false); progressDialog.setButton(DialogInterface.BUTTON_NEGATIVE, LocaleController.getString("Cancel", R.string.Cancel), new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { ConnectionsManager.getInstance().cancelRequest(reqId, true); donePressed = false; try { dialog.dismiss(); } catch (Exception e) { FileLog.e("tmessages", e); } } }); progressDialog.show(); } else if (currentStep == 1) { if (!isPrivate) { if (nameTextView.length() == 0) { AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); builder.setMessage(LocaleController.getString("ChannelPublicEmptyUsername", R.string.ChannelPublicEmptyUsername)); builder.setPositiveButton(LocaleController.getString("Close", R.string.Close), null); showDialog(builder.create()); return; } else { if (!lastNameAvailable) { Vibrator v = (Vibrator) getParentActivity() .getSystemService(Context.VIBRATOR_SERVICE); if (v != null) { v.vibrate(200); } AndroidUtilities.shakeView(checkTextView, 2, 0); return; } else { MessagesController.getInstance().updateChannelUserName(chatId, lastCheckName); } } } Bundle args = new Bundle(); args.putInt("step", 2); args.putInt("chat_id", chatId); presentFragment(new ChannelCreateActivity(args), true); } else { ArrayList<TLRPC.InputUser> result = new ArrayList<>(); for (Integer uid : selectedContacts.keySet()) { TLRPC.InputUser user = MessagesController .getInputUser(MessagesController.getInstance().getUser(uid)); if (user != null) { result.add(user); } } MessagesController.getInstance().addUsersToChannel(chatId, result, null); NotificationCenter.getInstance().postNotificationName(NotificationCenter.closeChats); Bundle args2 = new Bundle(); args2.putInt("chat_id", chatId); presentFragment(new ChatActivity(args2), true); } } } }); ActionBarMenu menu = actionBar.createMenu(); doneButton = menu.addItemWithWidth(done_button, R.drawable.ic_done, AndroidUtilities.dp(56)); if (currentStep != 2) { fragmentView = new ScrollView(context); ScrollView scrollView = (ScrollView) fragmentView; scrollView.setFillViewport(true); linearLayout = new LinearLayout(context); scrollView.addView(linearLayout, new ScrollView.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT)); } else { fragmentView = new LinearLayout(context); fragmentView.setOnTouchListener(new View.OnTouchListener() { @Override public boolean onTouch(View v, MotionEvent event) { return true; } }); linearLayout = (LinearLayout) fragmentView; } linearLayout.setOrientation(LinearLayout.VERTICAL); if (currentStep == 0) { actionBar.setTitle(LocaleController.getString("NewChannel", R.string.NewChannel)); fragmentView.setBackgroundColor(ContextCompat.getColor(context, R.color.card_background)); FrameLayout frameLayout = new FrameLayout(context); linearLayout.addView(frameLayout, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.WRAP_CONTENT)); avatarImage = new BackupImageView(context); avatarImage.setRoundRadius(AndroidUtilities.dp(32)); avatarDrawable.setInfo(5, null, null, false); avatarDrawable.setDrawPhoto(true); avatarImage.setImageDrawable(avatarDrawable); frameLayout.addView(avatarImage, LayoutHelper.createFrame(64, 64, Gravity.TOP | (LocaleController.isRTL ? Gravity.RIGHT : Gravity.LEFT), LocaleController.isRTL ? 0 : 16, 12, LocaleController.isRTL ? 16 : 0, 12)); avatarImage.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View view) { if (getParentActivity() == null) { return; } AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); CharSequence[] items; if (avatar != null) { items = new CharSequence[] { LocaleController.getString("FromCamera", R.string.FromCamera), LocaleController.getString("FromGalley", R.string.FromGalley), LocaleController.getString("DeletePhoto", R.string.DeletePhoto) }; } else { items = new CharSequence[] { LocaleController.getString("FromCamera", R.string.FromCamera), LocaleController.getString("FromGalley", R.string.FromGalley) }; } builder.setItems(items, new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialogInterface, int i) { if (i == 0) { avatarUpdater.openCamera(); } else if (i == 1) { avatarUpdater.openGallery(); } else if (i == 2) { avatar = null; uploadedAvatar = null; avatarImage.setImage(avatar, "50_50", avatarDrawable); } } }); showDialog(builder.create()); } }); nameTextView = new EditText(context); nameTextView.setHint(LocaleController.getString("EnterChannelName", R.string.EnterChannelName)); if (nameToSet != null) { nameTextView.setText(nameToSet); nameToSet = null; } nameTextView.setMaxLines(4); nameTextView .setGravity(Gravity.CENTER_VERTICAL | (LocaleController.isRTL ? Gravity.RIGHT : Gravity.LEFT)); nameTextView.setTextSize(TypedValue.COMPLEX_UNIT_DIP, 16); //nameTextView.setHintTextColor(0xff979797); nameTextView.setImeOptions(EditorInfo.IME_FLAG_NO_EXTRACT_UI); nameTextView.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_FLAG_CAP_SENTENCES); InputFilter[] inputFilters = new InputFilter[1]; inputFilters[0] = new InputFilter.LengthFilter(100); nameTextView.setFilters(inputFilters); nameTextView.setPadding(0, 0, 0, AndroidUtilities.dp(8)); AndroidUtilities.clearCursorDrawable(nameTextView); nameTextView.setTextColor(ContextCompat.getColor(context, R.color.primary_text)); frameLayout.addView(nameTextView, LayoutHelper.createFrame(LayoutHelper.MATCH_PARENT, LayoutHelper.WRAP_CONTENT, Gravity.CENTER_VERTICAL, LocaleController.isRTL ? 16 : 96, 0, LocaleController.isRTL ? 96 : 16, 0)); nameTextView.addTextChangedListener(new TextWatcher() { @Override public void beforeTextChanged(CharSequence s, int start, int count, int after) { } @Override public void onTextChanged(CharSequence s, int start, int before, int count) { } @Override public void afterTextChanged(Editable s) { avatarDrawable.setInfo(5, nameTextView.length() > 0 ? nameTextView.getText().toString() : null, null, false); avatarImage.invalidate(); } }); descriptionTextView = new EditText(context); descriptionTextView.setTextSize(TypedValue.COMPLEX_UNIT_DIP, 18); //descriptionTextView.setHintTextColor(0xff979797); descriptionTextView.setTextColor(ContextCompat.getColor(context, R.color.primary_text)); descriptionTextView.setPadding(0, 0, 0, AndroidUtilities.dp(6)); descriptionTextView.setGravity(LocaleController.isRTL ? Gravity.RIGHT : Gravity.LEFT); descriptionTextView.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_FLAG_CAP_SENTENCES | InputType.TYPE_TEXT_FLAG_MULTI_LINE | InputType.TYPE_TEXT_FLAG_AUTO_CORRECT); descriptionTextView.setImeOptions(EditorInfo.IME_ACTION_DONE); inputFilters = new InputFilter[1]; inputFilters[0] = new InputFilter.LengthFilter(120); descriptionTextView.setFilters(inputFilters); descriptionTextView .setHint(LocaleController.getString("DescriptionPlaceholder", R.string.DescriptionPlaceholder)); AndroidUtilities.clearCursorDrawable(descriptionTextView); linearLayout.addView(descriptionTextView, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.WRAP_CONTENT, 24, 18, 24, 0)); descriptionTextView.setOnEditorActionListener(new TextView.OnEditorActionListener() { @Override public boolean onEditorAction(TextView textView, int i, KeyEvent keyEvent) { if (i == EditorInfo.IME_ACTION_DONE && doneButton != null) { doneButton.performClick(); return true; } return false; } }); descriptionTextView.addTextChangedListener(new TextWatcher() { @Override public void beforeTextChanged(CharSequence charSequence, int i, int i2, int i3) { } @Override public void onTextChanged(CharSequence charSequence, int i, int i2, int i3) { } @Override public void afterTextChanged(Editable editable) { } }); TextView helpTextView = new TextView(context); helpTextView.setTextSize(TypedValue.COMPLEX_UNIT_DIP, 15); //helpTextView.setTextColor(0xff6d6d72); helpTextView.setGravity(LocaleController.isRTL ? Gravity.RIGHT : Gravity.LEFT); helpTextView.setText(LocaleController.getString("DescriptionInfo", R.string.DescriptionInfo)); linearLayout.addView(helpTextView, LayoutHelper.createLinear(LayoutHelper.WRAP_CONTENT, LayoutHelper.WRAP_CONTENT, LocaleController.isRTL ? Gravity.RIGHT : Gravity.LEFT, 24, 10, 24, 20)); } else if (currentStep == 1) { actionBar.setTitle(LocaleController.getString("ChannelSettings", R.string.ChannelSettings)); fragmentView.setBackgroundColor(ContextCompat.getColor(context, R.color.settings_background)); LinearLayout linearLayout2 = new LinearLayout(context); linearLayout2.setOrientation(LinearLayout.VERTICAL); linearLayout2.setBackgroundColor(ContextCompat.getColor(context, R.color.card_background)); linearLayout2.setElevation(AndroidUtilities.dp(2)); linearLayout.addView(linearLayout2, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.WRAP_CONTENT)); radioButtonCell1 = new RadioButtonCell(context); radioButtonCell1.setElevation(0); radioButtonCell1.setForeground(R.drawable.list_selector); radioButtonCell1.setTextAndValue(LocaleController.getString("ChannelPublic", R.string.ChannelPublic), LocaleController.getString("ChannelPublicInfo", R.string.ChannelPublicInfo), !isPrivate, false); linearLayout2.addView(radioButtonCell1, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.WRAP_CONTENT)); radioButtonCell1.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { if (!isPrivate) { return; } isPrivate = false; updatePrivatePublic(); } }); radioButtonCell2 = new RadioButtonCell(context); radioButtonCell2.setElevation(0); radioButtonCell2.setForeground(R.drawable.list_selector); radioButtonCell2.setTextAndValue(LocaleController.getString("ChannelPrivate", R.string.ChannelPrivate), LocaleController.getString("ChannelPrivateInfo", R.string.ChannelPrivateInfo), isPrivate, false); linearLayout2.addView(radioButtonCell2, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.WRAP_CONTENT)); radioButtonCell2.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { if (isPrivate) { return; } isPrivate = true; updatePrivatePublic(); } }); sectionCell = new ShadowSectionCell(context); linearLayout.addView(sectionCell, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.WRAP_CONTENT)); linkContainer = new LinearLayout(context); linkContainer.setOrientation(LinearLayout.VERTICAL); linkContainer.setBackgroundColor(ContextCompat.getColor(context, R.color.card_background)); linkContainer.setElevation(AndroidUtilities.dp(2)); linearLayout.addView(linkContainer, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.WRAP_CONTENT)); headerCell = new HeaderCell(context); linkContainer.addView(headerCell); publicContainer = new LinearLayout(context); publicContainer.setOrientation(LinearLayout.HORIZONTAL); linkContainer.addView(publicContainer, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, 36, 17, 7, 17, 0)); EditText editText = new EditText(context); editText.setText("telegram.me/"); editText.setTextSize(TypedValue.COMPLEX_UNIT_DIP, 18); //editText.setHintTextColor(0xff979797); editText.setTextColor(ContextCompat.getColor(context, R.color.primary_text)); editText.setMaxLines(1); editText.setLines(1); editText.setEnabled(false); editText.setBackgroundDrawable(null); editText.setPadding(0, 0, 0, 0); editText.setSingleLine(true); editText.setInputType(InputType.TYPE_TEXT_FLAG_MULTI_LINE | InputType.TYPE_TEXT_FLAG_AUTO_CORRECT); editText.setImeOptions(EditorInfo.IME_ACTION_DONE); publicContainer.addView(editText, LayoutHelper.createLinear(LayoutHelper.WRAP_CONTENT, 36)); nameTextView = new EditText(context); nameTextView.setTextSize(TypedValue.COMPLEX_UNIT_DIP, 18); //nameTextView.setHintTextColor(0xff979797); nameTextView.setTextColor(ContextCompat.getColor(context, R.color.primary_text)); nameTextView.setMaxLines(1); nameTextView.setLines(1); nameTextView.setBackgroundDrawable(null); nameTextView.setPadding(0, 0, 0, 0); nameTextView.setSingleLine(true); nameTextView.setInputType(InputType.TYPE_TEXT_VARIATION_EMAIL_ADDRESS | InputType.TYPE_TEXT_FLAG_MULTI_LINE | InputType.TYPE_TEXT_FLAG_AUTO_CORRECT); nameTextView.setImeOptions(EditorInfo.IME_ACTION_DONE); nameTextView.setHint( LocaleController.getString("ChannelUsernamePlaceholder", R.string.ChannelUsernamePlaceholder)); AndroidUtilities.clearCursorDrawable(nameTextView); publicContainer.addView(nameTextView, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, 36)); nameTextView.addTextChangedListener(new TextWatcher() { @Override public void beforeTextChanged(CharSequence charSequence, int i, int i2, int i3) { } @Override public void onTextChanged(CharSequence charSequence, int i, int i2, int i3) { checkUserName(nameTextView.getText().toString()); } @Override public void afterTextChanged(Editable editable) { } }); privateContainer = new TextBlockCell(context); privateContainer.setForeground(R.drawable.list_selector); privateContainer.setElevation(0); linkContainer.addView(privateContainer); privateContainer.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { if (invite == null) { return; } try { android.content.ClipboardManager clipboard = (android.content.ClipboardManager) ApplicationLoader.applicationContext .getSystemService(Context.CLIPBOARD_SERVICE); android.content.ClipData clip = android.content.ClipData.newPlainText("label", invite.link); clipboard.setPrimaryClip(clip); Toast.makeText(getParentActivity(), LocaleController.getString("LinkCopied", R.string.LinkCopied), Toast.LENGTH_SHORT) .show(); } catch (Exception e) { FileLog.e("tmessages", e); } } }); checkTextView = new TextView(context); checkTextView.setTextSize(TypedValue.COMPLEX_UNIT_DIP, 15); checkTextView.setGravity(LocaleController.isRTL ? Gravity.RIGHT : Gravity.LEFT); checkTextView.setVisibility(View.GONE); linkContainer.addView(checkTextView, LayoutHelper.createLinear(LayoutHelper.WRAP_CONTENT, LayoutHelper.WRAP_CONTENT, LocaleController.isRTL ? Gravity.RIGHT : Gravity.LEFT, 17, 3, 17, 7)); typeInfoCell = new TextInfoPrivacyCell(context); //typeInfoCell.setBackgroundResource(R.drawable.greydivider_bottom); linearLayout.addView(typeInfoCell, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.WRAP_CONTENT)); loadingAdminedCell = new LoadingCell(context); linearLayout.addView(loadingAdminedCell, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.WRAP_CONTENT)); adminedInfoCell = new TextInfoPrivacyCell(context); //adminedInfoCell.setBackgroundResource(R.drawable.greydivider_bottom); linearLayout.addView(adminedInfoCell, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.WRAP_CONTENT)); updatePrivatePublic(); } else if (currentStep == 2) { actionBar.setTitle(LocaleController.getString("ChannelAddMembers", R.string.ChannelAddMembers)); actionBar.setSubtitle(LocaleController.formatPluralString("Members", selectedContacts.size())); searchListViewAdapter = new SearchAdapter(context, null, false, false, false, false); searchListViewAdapter.setCheckedMap(selectedContacts); searchListViewAdapter.setUseUserCell(true); listViewAdapter = new ContactsAdapter(context, 1, false, null, false); listViewAdapter.setCheckedMap(selectedContacts); FrameLayout frameLayout = new FrameLayout(context); frameLayout.setBackgroundColor(ContextCompat.getColor(context, R.color.chat_list_background)); linearLayout.addView(frameLayout, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.WRAP_CONTENT)); nameTextView = new EditText(context); nameTextView.setTextSize(TypedValue.COMPLEX_UNIT_DIP, 16); //nameTextView.setHintTextColor(0xff979797); nameTextView.setTextColor(ContextCompat.getColor(context, R.color.primary_text)); nameTextView.setInputType(InputType.TYPE_TEXT_VARIATION_FILTER | InputType.TYPE_TEXT_FLAG_NO_SUGGESTIONS | InputType.TYPE_TEXT_FLAG_MULTI_LINE); nameTextView.setMinimumHeight(AndroidUtilities.dp(54)); nameTextView.setSingleLine(false); nameTextView.setLines(2); nameTextView.setMaxLines(2); nameTextView.setVerticalScrollBarEnabled(true); nameTextView.setHorizontalScrollBarEnabled(false); nameTextView.setPadding(0, 0, 0, 0); nameTextView.setHint(LocaleController.getString("AddMutual", R.string.AddMutual)); nameTextView.setTextIsSelectable(false); nameTextView.setImeOptions(EditorInfo.IME_ACTION_DONE | EditorInfo.IME_FLAG_NO_EXTRACT_UI); nameTextView .setGravity((LocaleController.isRTL ? Gravity.RIGHT : Gravity.LEFT) | Gravity.CENTER_VERTICAL); AndroidUtilities.clearCursorDrawable(nameTextView); frameLayout.addView(nameTextView, LayoutHelper.createFrame(LayoutHelper.MATCH_PARENT, LayoutHelper.WRAP_CONTENT, Gravity.LEFT | Gravity.TOP, 10, 0, 10, 0)); nameTextView.addTextChangedListener(new TextWatcher() { @Override public void beforeTextChanged(CharSequence charSequence, int start, int count, int after) { if (!ignoreChange) { beforeChangeIndex = nameTextView.getSelectionStart(); changeString = new SpannableString(charSequence); } } @Override public void onTextChanged(CharSequence charSequence, int i, int i2, int i3) { } @Override public void afterTextChanged(Editable editable) { if (!ignoreChange) { boolean search = false; int afterChangeIndex = nameTextView.getSelectionEnd(); if (editable.toString().length() < changeString.toString().length()) { String deletedString = ""; try { deletedString = changeString.toString().substring(afterChangeIndex, beforeChangeIndex); } catch (Exception e) { FileLog.e("tmessages", e); } if (deletedString.length() > 0) { if (searching && searchWas) { search = true; } Spannable span = nameTextView.getText(); for (int a = 0; a < allSpans.size(); a++) { ChipSpan sp = allSpans.get(a); if (span.getSpanStart(sp) == -1) { allSpans.remove(sp); selectedContacts.remove(sp.uid); } } actionBar.setSubtitle( LocaleController.formatPluralString("Members", selectedContacts.size())); listView.invalidateViews(); } else { search = true; } } else { search = true; } if (search) { String text = nameTextView.getText().toString().replace("<", ""); if (text.length() != 0) { searching = true; searchWas = true; if (listView != null) { listView.setAdapter(searchListViewAdapter); searchListViewAdapter.notifyDataSetChanged(); listView.setFastScrollAlwaysVisible(false); listView.setFastScrollEnabled(false); listView.setVerticalScrollBarEnabled(true); } if (emptyTextView != null) { emptyTextView .setText(LocaleController.getString("NoResult", R.string.NoResult)); } searchListViewAdapter.searchDialogs(text); } else { searchListViewAdapter.searchDialogs(null); searching = false; searchWas = false; listView.setAdapter(listViewAdapter); listViewAdapter.notifyDataSetChanged(); listView.setFastScrollAlwaysVisible(true); listView.setFastScrollEnabled(true); listView.setVerticalScrollBarEnabled(false); emptyTextView .setText(LocaleController.getString("NoContacts", R.string.NoContacts)); } } } } }); LinearLayout emptyTextLayout = new LinearLayout(context); emptyTextLayout.setVisibility(View.INVISIBLE); emptyTextLayout.setOrientation(LinearLayout.VERTICAL); linearLayout.addView(emptyTextLayout, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.MATCH_PARENT)); emptyTextLayout.setOnTouchListener(new View.OnTouchListener() { @Override public boolean onTouch(View v, MotionEvent event) { return true; } }); emptyTextView = new TextView(context); emptyTextView.setTextColor(0xff808080); emptyTextView.setTextSize(20); emptyTextView.setGravity(Gravity.CENTER); emptyTextView.setText(LocaleController.getString("NoContacts", R.string.NoContacts)); emptyTextLayout.addView(emptyTextView, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.MATCH_PARENT, 0.5f)); FrameLayout frameLayout2 = new FrameLayout(context); emptyTextLayout.addView(frameLayout2, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.MATCH_PARENT, 0.5f)); listView = new LetterSectionsListView(context); listView.setEmptyView(emptyTextLayout); listView.setVerticalScrollBarEnabled(false); listView.setDivider(null); listView.setDividerHeight(0); listView.setFastScrollEnabled(true); listView.setScrollBarStyle(View.SCROLLBARS_OUTSIDE_OVERLAY); listView.setAdapter(listViewAdapter); listView.setFastScrollAlwaysVisible(true); listView.setVerticalScrollbarPosition( LocaleController.isRTL ? ListView.SCROLLBAR_POSITION_LEFT : ListView.SCROLLBAR_POSITION_RIGHT); linearLayout.addView(listView, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.MATCH_PARENT)); listView.setOnItemClickListener(new AdapterView.OnItemClickListener() { @Override public void onItemClick(AdapterView<?> adapterView, View view, int i, long l) { TLRPC.User user; if (searching && searchWas) { user = (TLRPC.User) searchListViewAdapter.getItem(i); } else { int section = listViewAdapter.getSectionForPosition(i); int row = listViewAdapter.getPositionInSectionForPosition(i); if (row < 0 || section < 0) { return; } user = (TLRPC.User) listViewAdapter.getItem(section, row); } if (user == null) { return; } boolean check = true; if (selectedContacts.containsKey(user.id)) { check = false; try { ChipSpan span = selectedContacts.get(user.id); selectedContacts.remove(user.id); SpannableStringBuilder text = new SpannableStringBuilder(nameTextView.getText()); text.delete(text.getSpanStart(span), text.getSpanEnd(span)); allSpans.remove(span); ignoreChange = true; nameTextView.setText(text); nameTextView.setSelection(text.length()); ignoreChange = false; } catch (Exception e) { FileLog.e("tmessages", e); } } else { ignoreChange = true; ChipSpan span = createAndPutChipForUser(user); if (span != null) { span.uid = user.id; } ignoreChange = false; if (span == null) { return; } } actionBar.setSubtitle(LocaleController.formatPluralString("Members", selectedContacts.size())); if (searching || searchWas) { ignoreChange = true; SpannableStringBuilder ssb = new SpannableStringBuilder(""); for (ImageSpan sp : allSpans) { ssb.append("<<"); ssb.setSpan(sp, ssb.length() - 2, ssb.length(), SpannableStringBuilder.SPAN_EXCLUSIVE_EXCLUSIVE); } nameTextView.setText(ssb); nameTextView.setSelection(ssb.length()); ignoreChange = false; searchListViewAdapter.searchDialogs(null); searching = false; searchWas = false; listView.setAdapter(listViewAdapter); listViewAdapter.notifyDataSetChanged(); listView.setFastScrollAlwaysVisible(true); listView.setFastScrollEnabled(true); listView.setVerticalScrollBarEnabled(false); emptyTextView.setText(LocaleController.getString("NoContacts", R.string.NoContacts)); } else { if (view instanceof UserCell) { ((UserCell) view).setChecked(check, true); } } } }); listView.setOnScrollListener(new AbsListView.OnScrollListener() { @Override public void onScrollStateChanged(AbsListView absListView, int i) { if (i == SCROLL_STATE_TOUCH_SCROLL) { AndroidUtilities.hideKeyboard(nameTextView); } if (listViewAdapter != null) { listViewAdapter.setIsScrolling(i != SCROLL_STATE_IDLE); } } @Override public void onScroll(AbsListView absListView, int firstVisibleItem, int visibleItemCount, int totalItemCount) { if (absListView.isFastScrollEnabled()) { AndroidUtilities.clearDrawableAnimation(absListView); } } }); } return fragmentView; }