UIView का एक उप केंद्र कैसे केंद्रित करें


128

मैं एक है UIViewएक के अंदर UIViewमीटर और मैं भीतरी चाहते UIViewहमेशा बाहरी एक के अंदर केंद्र पर किया जाना है, यह चौड़ाई और ऊंचाई का आकार बदलने के बिना।

मैंने स्ट्रट्स और स्प्रिंग्स को सेट किया है ताकि यह आकार / सेट / बाईं / दाईं ओर / नीचे के आकार को बिना सेट किए हुए हो। लेकिन यह अभी भी केंद्र नहीं है। कोई उपाय?


2
स्वीकृत उत्तर गलत है और दुर्घटनाग्रस्त हो जाएगा। हेजाज़ी का जवाब बहुत अच्छा काम करता है।
फेटी

जवाबों:


209

उद्देश्य सी

yourSubView.center = CGPointMake(yourView.frame.size.width  / 2, 
                                 yourView.frame.size.height / 2);

तीव्र

yourSubView.center = CGPoint(x: yourView.frame.size.width  / 2,
                             y: yourView.frame.size.height / 2)

51
आप का उपयोग करना चाहिए boundsऔर नहीं frame, के रूप में frameअपरिभाषित है अगर दृश्य एक है transform
ओम

1
यह वास्तव में इस मामले में एक अलग नहीं करेगा, जैसा कि केवल sizeउपयोग किया जा रहा है।
पीटर डेविस

1
इससे कोई फर्क नहीं पड़ता, frameयदि दृश्य transformपहचान नहीं है तो पूरी संपत्ति अपरिभाषित है; UIView की फ़्रेम प्रॉपर्टी पर प्रलेखन पढ़ें ।
ओम

6
दुर्भाग्य से यह उत्तर वास्तव में गलत है । बस हेजा के सही उत्तर का उपयोग करें।
फटी

@ फटी क्या यहाँ बिल्कुल गलत है? मैंने एक दृश्य के भीतर एक ImageView केंद्रित करने के लिए इसका इस्तेमाल किया और यह काम कर रहा है।
jreft56

284

आप यह कर सकते हैं और यह हमेशा काम करेगा:

child.center = [parent convertPoint:parent.center fromView:parent.superview];

और स्विफ्ट के लिए:

child.center = parent.convert(parent.center, from:parent.superview)

1
और बाद में मत भूलना, child.frame = CGRectIntegral (child.frame);
फेटी

8
एक: यह केवल तभी काम करता है जब आपने अपने मूल दृश्य के केंद्र / स्थान को नहीं बदला हो। दूसरा: यदि आप इस पद्धति का उपयोग कर रहे हैं तो बिंदु को परिवर्तित करने की कोई आवश्यकता नहीं है (यह पहले से ही सही प्रारूप में है) बस उपयोग करें child.center = parent.center। मैं `child.center = CGPointMake (parent.bounds.height / 2, parent.bounds. उपलब्धता / 2 ') का उपयोग करूँगा। यह आपके पैरेंट व्यू सेंटर के सेट होने की परवाह किए बिना आपके सबवे को केंद्रित करेगा।
पुराना नाम

1
यह भी उपयोगी नहीं है अगर दृश्य को पदानुक्रम में अभी तक जोड़ा नहीं गया है (जैसे कि वस्तु को अंदर करते समय)
विक्टर जलकेन

1
@ हेजाज़ी को भी अच्छा जवाब देना अच्छा लगेगा;)
मिलाद फरीदिया

1
@Soumen नहीं, अंतर है। दृश्य केUIView.bounds सापेक्ष ही है (और इसलिए bounds.originशुरू में शून्य है), जबकि पर्यवेक्षणUIView.center के समन्वय प्रणाली में निर्दिष्ट है ।
हिजाज़ी

41

शुरू करने से पहले, आइए याद दिलाते हैं कि मूल बिंदु CGPointएक दृश्य का ऊपरी बाएं कोने है। विचारों और माता-पिता के बारे में समझने के लिए एक महत्वपूर्ण बात।

आइए इस सरल कोड पर एक नज़र डालें, एक दृश्य नियंत्रक जो इसे एक काले वर्ग को देखने के लिए जोड़ता है:

class ViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()
        // Do any additional setup after loading the view, typically from a nib.
        createDummyView()
        super.view.backgroundColor = UIColor.cyanColor();
    }

    func createDummyView(){
        var subView = UIView(frame: CGRect(x: 15, y: 50, width: 50 , height: 50));
        super.view.addSubview(subView);
        view.backgroundColor = UIColor.blackColor()
    }

}

यह इस दृश्य को बनाएगा: काले आयत की उत्पत्ति और केंद्र समान निर्देशांक फिट करते हैं जैसे कि यह माता-पिता हैं

यहाँ छवि विवरण दर्ज करें

अब चलिए सबवू व्यू को सब व्यू में जोड़ने की कोशिश करते हैं, और सबव्यू को सबव्यू के रूप में एक ही मूल में देते हैं, लेकिन सब व्यू को सब व्यू के एक बच्चे का दृश्य बनाते हैं।

हम यह कोड जोड़ेंगे:

var subSubView = UIView();
subSubView.frame.origin = subView.frame.origin;
subSubView.frame.size = CGSizeMake(20, 20);
subSubView.backgroundColor = UIColor.purpleColor()
subView.addSubview(subSubView)

और यह परिणाम है:

यहाँ छवि विवरण दर्ज करें

इस लाइन के कारण:

subSubView.frame.origin = subView.frame.origin;

आप बैंगनी आयत की उत्पत्ति के समान होने की उम्मीद करते हैं क्योंकि यह माता-पिता (काली आयत) है, लेकिन यह इसके तहत जाता है, और ऐसा क्यों है? क्योंकि जब आप किसी अन्य दृश्य में एक दृश्य जोड़ते हैं, तो सब व्यू फ्रेम "दुनिया" अब यह मूल BOUND RECTANGLE है, यदि आपके पास एक दृश्य है कि यह मुख्य स्क्रीन पर उत्पन्न हुआ है, तो इसे सब व्यूज के लिए कोर्ड्स (15,15) पर है। ऊपरी बाएं कोने (0,0) होगा

यही कारण है कि आपको हमेशा आयत से बंधे माता-पिता को संदर्भित करने की आवश्यकता होती है, जो कि यह सब-व्यूज की "दुनिया" है, इस लाइन को ठीक करने देता है:

subSubView.frame.origin = subView.bounds.origin;

और जादू देखें, सबस्यूव्यू अब मूल माता-पिता में बिल्कुल स्थित है:

यहाँ छवि विवरण दर्ज करें

तो, आपको पसंद है "ठीक है, मैं केवल अपने माता-पिता के दृष्टिकोण से अपना दृष्टिकोण केंद्रित करना चाहता था, बड़ी बात क्या है?" ठीक है, यह कोई बड़ी बात नहीं है, आपको बस मूल केंद्र बिंदु को "ट्रांसलेट" करने की ज़रूरत है जो इसे करने के लिए माता-पिता की सीमा केंद्र से फ्रेम में लिया गया है:

subSubView.center = subView.convertPoint(subView.center, fromView: subSubView);

आप वास्तव में उसे "माता-पिता को देखने के केंद्र में ले जाने, और इसे सबसुव्यू वर्ल्ड में बदलने" के लिए कह रहे हैं।

और आपको यह परिणाम मिलेगा:

यहाँ छवि विवरण दर्ज करें


जहां लाइन 'subSubView.center = subView.convertPoint (subView.center, fromView: subSubView)' को रखा जाए?
थामराई टी

26

मै इस्तेमाल करूंगा:

self.childView.center = CGPointMake(CGRectGetMidX(self.parentView.bounds),
                                    CGRectGetMidY(self.parentView.bounds));

मुझे CGRectविकल्पों का उपयोग करना पसंद है ...

स्विफ्ट 3:

self.childView.center = CGPoint(x: self.parentView.bounds.midX,
                                        y: self.parentView.bounds.midY);

19

1. यदि आपके पास ऑटो-आउट सक्षम है:

  • संकेत: ऑटोलेयूट के साथ किसी अन्य दृश्य पर दृश्य केंद्रित करने के लिए आप कम से कम एक अभिभावक दृश्य साझा करने वाले किसी भी दो दृश्य के लिए एक ही कोड का उपयोग कर सकते हैं।

सबसे पहले बच्चे को अक्षम करने के लिए ऑटोरेस्पोन्डिंग देखें

UIView *view1, *view2;
[childview setTranslatesAutoresizingMaskIntoConstraints:NO];
  1. यदि आप UIView + ऑटोलैयूट या प्यूरलेआउट हैं :

    [view1 autoAlignAxis:ALAxisHorizontal toSameAxisOfView:view2];
    [view1 autoAlignAxis:ALAxisVertical toSameAxisOfView:view2];
  2. यदि आप केवल UIKit स्तर के ऑटोलैयट तरीकों का उपयोग कर रहे हैं:

    [view1 addConstraints:({
        @[ [NSLayoutConstraint
           constraintWithItem:view1
           attribute:NSLayoutAttributeCenterX
           relatedBy:NSLayoutRelationEqual
           toItem:view2
           attribute:NSLayoutAttributeCenterX
           multiplier:1.f constant:0.f],
    
           [NSLayoutConstraint
            constraintWithItem:view1
            attribute:NSLayoutAttributeCenterY
            relatedBy:NSLayoutRelationEqual
            toItem:view2
            attribute:NSLayoutAttributeCenterY
            multiplier:1.f constant:0.f] ];
    })];

2. ऑटोलॉयआउट के बिना:

मैं पसंद करता हूं:

UIView *parentView, *childView;
[childView setFrame:({
    CGRect frame = childView.frame;

    frame.origin.x = (parentView.frame.size.width - frame.size.width) / 2.0;
    frame.origin.y = (parentView.frame.size.height - frame.size.height) / 2.0;

    CGRectIntegral(frame);
})];

6
यह ध्यान दिया जाना चाहिए कि, स्वीकृत उत्तर के विपरीत, यह समाधान पिक्सेल सीमाओं पर सफाई से संरेखित करेगा और अन्य चौड़ाई के लिए दृश्य के धुंधलापन को रोक देगा।
ब्रैड लार्सन

1
अगर मैं गलत नहीं हूँ, child.frame = CGRectIntegral (child.frame); समस्या बीएल का वर्णन करने के लिए कहीं भी पकड़ने / सभी का उपयोग करने का एक सुंदर प्रकार है।
फटी

1
@JoeBlow: सिर के लिए धन्यवाद। मुझे गोलाई पसंद थी लेकिन ब्लॉक स्टाइल के साथ इसका उपयोग करना अधिक सुरुचिपूर्ण थाCGRectIntegral
सेमल इकर

क्या आप फ्रेम को सेट करने के लिए आपके द्वारा उपयोग किए गए सिंटैक्स की व्याख्या कर सकते हैं, मैंने इसे पहले नहीं देखा। क्या यह हमेशा "क्लोजर" में अंतिम विवरण है जो संपत्ति को सौंपा गया है? और मैं इसे Apple डॉक्स में कहां खोज सकता हूं?
जोहान्स

"यदि आप केवल UIKit स्तर के ऑटोलैयट तरीकों का उपयोग कर रहे हैं:" परिणाम में त्रुटियां हैं।
जॉनी

13

सबसे आसान तरीका:

child.center = parent.center

मेरा मतलब है कि आपको और अधिक स्पष्टीकरण / विवरण जोड़ना चाहिए कि यह कैसे काम करता है।
तुषार

इस प्रकार के बहुत सारे उत्तरों की खोज की, इस सरल ने मेरे लिए चाल चली। धन्यवाद।
gbossa

9

यहाँ छवि विवरण दर्ज करें

अपने आंतरिक दृश्य के लिए इस ऑटोरेस्पिरिंग मास्क को सेट करें।


1
ऑटोलॉयउट के साथ, कोई ऑटोसाइज़िंग विंडो नहीं है।
एलन

@ यदि आपको ऑटोरेस्ज़िंग का उपयोग करना है तो आपको ऑटोलेयूट को निष्क्रिय करना होगा।
मयंक जैन

8

IOS9 के साथ आप लेआउट एंकर एपीआई का उपयोग कर सकते हैं।

कोड इस तरह दिखेगा:

childview.centerXAnchor.constraintEqualToAnchor(parentView.centerXAnchor).active = true
childview.centerYAnchor.constraintEqualToAnchor(parentView.centerYAnchor).active = true

इस ओवर का फायदा CGPointMakeया CGRectयह है कि उन तरीकों से आप व्यू का केंद्र एक स्थिरांक पर सेट कर रहे हैं, लेकिन इस तकनीक के साथ आप उन दो विचारों के बीच संबंध स्थापित कर रहे हैं, जो हमेशा के लिए parentviewबदल जाएंगे, फिर चाहे वह कैसा भी बदलाव क्यों न हो।

इससे पहले कि आप ऐसा करने के लिए सुनिश्चित करें:

        self.view.addSubview(parentView)
        self.view.addSubView(chidview)

और translatesAutoresizingMaskIntoConstraintsझूठ के लिए प्रत्येक दृश्य के लिए सेट करने के लिए।

इससे दुर्घटनाग्रस्त होने और ऑटोलेयूट को हस्तक्षेप करने से रोका जा सकेगा।


8

आप उपयोग कर सकते हैं

yourView.center = CGPointMake(CGRectGetMidX(superview.bounds), CGRectGetMidY(superview.bounds))

और स्विफ्ट 3.0 में

yourView.center = CGPoint(x: superview.bounds.midX, y: superview.bounds.midY)

1
दूसरा कोड उदाहरण पूरी तरह से तेजी से काम करता है 4. महान perfectly!
३४

हाँ! धन्यवाद, आखिरकार। उस midX / midY चीज के बारे में नहीं जानते थे। Perfecto।
डेव वाई

5

दृश्य और सबव्यू में एक ही केंद्र का उपयोग करना इसे करने का सबसे सरल तरीका है। आप ऐसा कुछ कर सकते हैं,

UIView *innerView = ....;
innerView.view.center = self.view.center;
[self.view addSubView:innerView];

यह सुपर दृश्य के संबंध में उप दृश्य को केंद्र में रखेगा। उपरोक्त मामले में, यह काम कर रहा है क्योंकि मूल (0, 0) पर है।
अब्दुर्रहमान मुबीन अली

3

PureLayout का उपयोग करने के साथ एक और समाधान autoCenterInSuperview

// ...
UIView *innerView = [UIView newAutoLayoutView];
innerView.backgroundColor = [UIColor greenColor];
[innerView autoSetDimensionsToSize:CGSizeMake(100, 30)];

[outerview addSubview:innerView];

[innerView autoCenterInSuperview];

यह ऐसा है कि यह कैसा दिखता है:

PureLayout के साथ केंद्र



1

मै इस्तेमाल करूंगा:

child.center = CGPointMake(parent.bounds.height / 2, parent.bounds.width / 2)

यह सरल, छोटा और मीठा है। यदि आप @ हज्जाजी के उत्तर का उपयोग करते हैं और आपके सबव्यू के parent.centerअलावा किसी अन्य चीज़ पर सेट है तो (0,0)वह केंद्रित नहीं होगा!


0
func callAlertView() {

    UIView.animate(withDuration: 0, animations: {
        let H = self.view.frame.height * 0.4
        let W = self.view.frame.width * 0.9
        let X = self.view.bounds.midX - (W/2)
        let Y = self.view.bounds.midY - (H/2)
        self.alertView.frame = CGRect(x:X, y: Y, width: W, height: H)
        self.alertView.layer.borderWidth = 1
        self.alertView.layer.borderColor = UIColor.red.cgColor
        self.alertView.layer.cornerRadius = 16
        self.alertView.layer.masksToBounds = true
        self.view.addSubview(self.alertView)

    })


}// calculation works adjust H and W according to your requirement
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.